Appendix A. C# and VB.NET Language Features

ASP.NET MVC takes advantage of many advanced features of the C# and VB.NET languages. Some of these features were not introduced into these languages until C# 3.0 and Visual Basic 9.0. This appendix provides you with a brief overview of these new language features.

Type Inference

Both C# and Visual Basic can infer the type of a variable when you create a local variable. For example, the following line of code creates a new string variable named message with the value "Hello World!":

(C#)

var message = "Hello World!";


(VB)

Dim message = "Hello World!"


Notice that you do not need to specify the type of the message variable. The compiler figures out the type from "Hello World!" automatically.

There are no performance drawbacks from using type inference. The type is inferred at compile time and not runtime. In particular, using type inference does not result in late binding.

Type inference is a good way to remove some of the redundancy in the C# language. Consider the following statement:

(C#)

ArrayList countries = new ArrayList();


(VB)

Dim countries As New ArrayList()


In the case of C#, the type of the countries variable is specified twice: on both sides of the = sign. Using type inference removes this redundancy with no drawbacks in performance:

(C#)

var countries = new ArrayList();


Object Initializers

Object initializers provide you with shorthand syntax for creating a new object and setting one or more properties on the object. Imagine, for example, that you want to create an instance of a Customer class and set the FirstName and LastName properties. Normally, you would have to write the following code:

(C#)

Customer customer1 = new Customer();
customer1.FirstName = "Scott";
customer1.LastName = "Guthrie";


(VB)

Dim customer1 As New Customer()
customer1.FirstName = "Scott"
customer1.LastName = "Guthrie"


By taking advantage of the new object initialize syntax, you can reduce the three lines of code to a single line:

(C#)

Customer customer1 = new Customer() { FirstName="Scott", LastName="Guthrie"};


(VB)

Dim customer1 As New Customer() With {.FirstName = "Scott", .LastName = "Guthrie"}


Anonymous Types

Anonymous types give you a compact way to define a new class and create a new instance of the new class at the same time. For example, the following line of code both creates a new type of class and instantiates an instance of the new class at the same time:

(C#)

var product1 = new { Name = "Netbook", Price = 344.99m };


(VB)

Dim product1 = New With {.Name = "Netbook", .Price = 344.99}


This single line of code is equivalent to first creating a new class:

(C#)

image


(VB)

image


And then creating an instance of the new class:

(C#)

var product1 = new Product {Name="Netbook", Price=344.99m};


(VB)

Dim product1 = New Product With {.Name = "Netbook", .Price = 344.99}


Obviously, using anonymous types takes far, far less typing to accomplish the same work.

Two anonymous types that have the same properties, in the same order, are the same type. For example, product1 and product2 are the same type:

(C#)

image


(VB)

image


However, sandwich1, sandwich2, and sandwich3 are all different types; the order of the properties is different in the case of sandwich1 and sandwich2:

(C#)

image


(VB)

image


Anonymous types are used extensively in the ASP.NET MVC framework. For example, you can specify a set of HTML attributes when using an HTML helper by using an anonymous type:

(C#)

<%= Html.TextArea("Comments", new {cols="50", rows="10"}) %>


(VB)

<%=Html.TextArea("Comments", New With {.cols = "50", .rows = "10"})%>


When this Html.TextArea() helper renders an HTML textarea, the textarea is rendered with cols="50" and rows="10" attributes.

Note

When creating anonymous types with Visual Basic, you can use the Key keyword to mark certain properties as key properties. A key property is used to determine when two instances of the same anonymous type are equal. If two instances of the same anonymous type have the same values for their key properties, then the two instances are equal.

Nullable Types

Reference types, such as a string, can accept the value null (Nothing). Value types, such as an integer or DateTime, normally cannot accept the value null (Nothing).

By taking advantage of nullable types, you can assign the value null to a value type like an integer or DateTime. For example, the following line of code creates a nullable DateTime named dateReleased:

(C#)

DateTime? dateReleased = null;


(VB)

Dim dateReleased As DateTime? = Nothing


The question mark indicates that the dateReleased variable represents a nullable type instead of a value type.

You can use nullable types with method parameters. For example, you can use a nullable type with an ASP.NET MVC action parameter like this:

(C#)

image


(VB)

image


You can invoke this action using either of the following URLs:

/Home/Index

/Home/Index/22

Because the Index action accepts a nullable parameter, invoking the action without supplying a parameter does not result in an error.

Notice how the action uses the HasValue and Value properties. You use HasValue to determine if a nullable type has the value null (Nothing). You use the Value property to get the non-nullable type from the nullable type.

Extension Methods

Extension methods enable you to add new functionality to an existing class without deriving a new class. In other words, extension methods enable you to extend an existing class with new methods.

In the ASP.NET MVC framework, all the helper methods are implemented as extension methods. For example, the Html.TextBox() helper method is an extension method that extends the HtmlHelper class.

You create extension methods in different ways when using C# versus Visual Basic. When working with C#, you create an extension method by creating a static class with a static method.

(C#)

image


Notice that the first parameter is qualified by the this keyword. The this keyword indicates that the Button() extension method extends the HtmlHelper class. The Button() method becomes a method of the HtmlHelper class.

You create an extension method with Visual Basic by creating a module:

(VB)

image


Notice that the Button() method is decorated with the System.Runtime.CompilerServices.Extension attribute.

To use an extension method, you must remember to import the namespace of the extension method. For example, if you want to use the Html.Button() helper method in a view, then you must import the Helpers namespace in the view using the Import directive like this:

<%@ Import Namespace="MvcApplication1.Helpers" %>


After you import an extension method, the extension method appears in Intellisense just like any other method (see Figure A.1).

Figure A.1. Using the Button() extension method

image

Generics

A generic is a class, structure, interface, or method that accepts one or more type parameters. If you have worked with generic collections, you are already familiar with generics. For example, the generic List collection, which you can use to represent a list of items of a particular type, is a generic class:

(C#)

var shoppingList = new List<string>();


(VB)

Dim shoppingList As New List(Of String)()


When you create a generic List, you specify the type of item that the list represents. In the preceding code, the List represents a list of strings.

Generics is another language feature that is used extensively in the ASP.NET MVC framework. For example, the ViewPage class—the base class for views—is a generic class. When you create a view, you supply a generic type parameter for the ViewPage class in the <%@ Page %> directive like this:

(C#)

image


(VB)

image


In this case, we actually have two generic type parameters. Both the ViewPage class and the IEnumerable interface accept a generic type parameter.

The generic type parameter is used by the ViewPage class to cast the Model property to a particular type. In this case, the Model property is cast to a collection (IEnumerable) of Product items.

Lambda Expressions

A lambda expression provides you with a compact way to express a function. You can use a lambda expression to represent a function like this:

(C#)

x => x * 2


(VB)

Function(x) x * 2


This expression represents a function that accepts a parameter named x and times x by two. This lambda expression is equivalent to the following function:

(C#)

image


(VB)

image


Note

The C# => operator is pronounced as the “goes to” operator.

Lambda expressions are used most often with LINQ. See the next section to learn about LINQ.

LINQ

LINQ (Language INtegrated Query) enables you to perform operations on a set of objects. The objects could be a set of database records. By taking advantage of LINQ, you can write all your database logic within the C# or Visual Basic language, and you never need to write any SQL code again.

The System.Linq namespace contains two classes named Enumerable and Queryable. The Enumerable class contains a set of extension methods for the IEnumerable<T> interface. For example, the Enumerable class includes the following extension methods (this is not even close to being a complete list):

Average()

Count()

First()

Last()

Max()

Min()

OrderBy()

Select()

Sum()

Where()

Because these are extension methods on the IEnumerable<T> interface, you can use these methods on any class that implements the IEnumerable<T> interface including the generic List class:

(C#)

image


(VB)

image


This code creates a generic List class that represents a set of products. The Enumerable extension methods are used to retrieve a set of products where each product has a price greater than $50.00 and the products are ordered by name. Therefore, you get the following products in the following order: Chair, Laptop.

Notice that the LINQ methods use lambda expressions. For example, the Where() method accepts a lambda expression (a function) that returns a Boolean value. The lambda expression is used to filter the set of products.

The Queryable class contains a similar set of extension methods; however, these methods extend any class that implements the IQueryable<T> interface.

Both the Microsoft Entity Framework and Microsoft LINQ to SQL represent database tables with classes that implement the IQueryable<T> interface. That means that you can use these extension methods with either technology.

For example, here is how you would retrieve a set of database records by using the Queryable extension methods with the Microsoft Entity Framework:

(C#)

image


(VB)

image


The query retrieves all the movies that have a title that starts with the letter T and orders the results by the date the movie was released.

Instead of using the Enumerable or Queryable extension methods directly, you can use the new query syntax language features introduced into the C# and Visual Basic languages. In other words, there are two ways to execute a LINQ query: method syntax and query syntax.

The following code uses query syntax to retrieve the same set of movies that we retrieved earlier using method syntax:

(C#)

image


(VB)

image


You might find query syntax more readable than method syntax. There is no difference in performance. Your choice between method and query syntax is purely a preference issue.

When you use LINQ against a database, the query is translated into a SQL query and executed. When you retrieve a set of database records, the SQL query is not executed until you actually start iterating through the results (for example, by using a for each loop).

This is an important point: LINQ does not load an entire database table into memory and then perform operations on the loaded data. Instead, LINQ waits until the last possible moment to execute a query. Just before you start to iterate through the results of a query, LINQ analyzes your query and converts it into the most efficient SQL query possible and then executes the SQL query against the database.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
18.191.33.136