New Language Features in C# 2.0, Part 1

Four years ago, a new upstart language named C# surprised the development world
with its elegance and consistency. Now that Microsoft has released a technology
preview version of Visual Studio 2005 (formerly codenamed Whidbey), .NET's favorite
language is back with some new innovations. In this two-part series, you'll
get a first look at three of the four major language refinements in the latest
version of C#.

Anonymous Methods

In .NET programming, every executable line of code takes place inside of a
method, and every method is explicitly declared at the class level -- until
now. In C# 2.0, you can declare a method inside of another piece of code, where a
delegate is expected. This embedded method is called an anonymous
method. (Anonymous methods will look familiar to you if you've used lambda
functions in the Lisp programming language.)

Anonymous methods are primarily useful if you want to quickly hook up an
event handler. For example, here's the standard way to hook up an event handler that responds to
the click of a button (in any version of .NET):

In this example, there are two methods. Form1() initializes the window and
connects the event handlers. ButtonClick() receives the event when the user
clicks the button.

Here's how you could rewrite this example using an anonymous method:

public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
button1.Click += delegate(object sender, EventArgs e)
{
// The following code is part of an anonymous method.
MessageBox.Show("You clicked the button, and " +
"This is an anonymous method!");
};
}
}

Notice that the event handler method is defined inside of Form1(), and is attached directly to the Click event. The anonymous method starts with the keyword
delegate, followed by the parameter list and then the actual method code.
Essentially, the Form1() method defines a new method, but doesn't execute it. (In
this example, the code in the anonymous method won't run until the Click event
fires.)

When you declare an anonymous method, the C# compiler has some liberty to
decide how it handles the situation. In this example, the compiler creates a new,
uniquely named method in the Form1 class. This anonymous method has
access to all the public and private member variables and properties of the
Form1 class.

Even more interestingly, the anonymous method also has access to local
variables defined in the procedure where the anonymous method is declared.
Here's an example that shows this somewhat counterintuitive ability:

To make this work, the C# compiler handles this code a little differently. It
actually creates a new class that it nests inside of the Form1 class. It adds the
anonymous method to the new class, along with a private member variable to store
the contents from tempVar.

You don't need to attach an anonymous method to an event. You can also
declare an anonymous method and assign it to a delegate variable. This technique
is useful if you need to pass a delegate as a callback, or if you want to attach
the same anonymous method to two event handlers, as shown here:

Overall, anonymous methods make most sense if your method code is relatively
short; otherwise, it can be difficult to distinguish the embedded anonymous
method code from the surrounding method code. One reason you might want to use
anonymous methods is to simplify the handling of asynchronous events. Using an
anonymous method, you can define how you want to handle the completion of an asynchronous
task in the same context where you start the asynchronous task. This approach
can clarify your code.

Iterators

Often, developers need to create classes that support enumeration. When a
class supports enumeration, you can use the convenient foreach syntax to
step through a group of items. For example, if you create an OrderCatalog class
that contains a group of OrderItem instances, you might want to enumerate over
all of the items using this code:

foreach (item OrderItem in catalog)
{
// (Process OrderItem here.)
}

This code gets translated by the C# compiler to use the GetEnumerator()
method of the class. Technically, it looks like this:

As a result, this pattern only works with classes that implement the
IEnumerable interface. Creating a class that supports enumeration in C# 1.0
ranges from mildly inconvenient to annoyingly awkward. In C# 2.0, a new language
feature known as iterators makes it much easer to create classes that
support enumeration. Instead of building a state machine to keep track of your
position in a collection, you create one public method named GetEnumerator()
that returns all of the values directly using the new yield return keyword.

For example, here's a simple class that yields three pieces of information:

When you use foreach on a DecoratingColors instance, you'll wind up
with three strings, one after the other.

To see the real rewards of iterators, you need to consider a more realistic
example. The following code shows the OrderCatalog class, which contains a
private collection of OrderItem instances. In this example, the GetEnumerator() method traverses all the items in the private collection in a loop, returning
one item each time.

The beauty of iterators is that the enumerable class can concentrate on
providing information, while the consumer can concentrate on retrieving it.
Neither part needs to worry about the actual implementation details of how
positioned is maintained.

Partial Classes

Partial classes give you the ability to split a single class into more
than one source code (.cs) file. Here's what a partial class looks like when
it's split over two files:

When you build the application, Visual Studio .NET tracks down each piece of
MyClass and assembles it into a complete, compiled class with two methods,
MethodA() and MethodB().

Partial classes don't offer much in the way of solving programming problems,
but they can be useful if you have extremely large, unwieldy classes. (Of
course, this might be a sign that you haven't properly factored your problem, in
which case you should really break your class down into separate classes.) The
real purpose of partial classes in .NET is to hide automatically generated designer
code.

For example, if you build a .NET form in Visual Studio 2005, your event-
handling code is placed in the source code file for the form, but the designer
code that creates and configures each control and connects the event handlers is
nowhere to be seen. In order to see this code, you need to select Project-->Show All Files from the Visual Studio menu. When you do, a new file appears with
the other half of the class. For example, if you create a new form named Form1,
you'll actually wind up with a Form1.cs file for your code and a
Form1.Designer.cs file that contains the automatically generated part.

Summary

In the next article in this series, you'll learn about the sexiest new language feature in
C# (and no, it isn't multiple inheritance). In the meantime, for a more detailed look at the C# language rules, surf to the C# language page at
MSDN, at
msdn.microsoft.com/vcsharp/team/language. You'll find a link that
allows you to download a detailed white paper on the new C# language
specifications, along with useful insight from the C# language designers in the
"Ask a Language Designer" section of the site.

Matthew MacDonald
is a developer, author, and educator in all things Visual Basic and .NET. He's worked with Visual Basic and ASP since their initial versions, and written over a dozen books on the subject, including The Book of VB .NET (No Starch Press) and Visual Basic 2005: A Developer's Notebook (O'Reilly). His web site is http://www.prosetech.com/.