Welcome to MSDN Blogs Sign in | Join | Help

C# 3.0: I like Extension Methods

After the declaration of C# 3.0 I went ahead and installed the PDC bits. After reading through the language spec. I was very very very unhappy. I mean we were just getting excited over C#2.0 supporting generics, anonymous mehtods, Nullable types and then suddenly someone ruins all the fun by showing us C#3.0. C#2.0 already appears stale. Some great blogs on this are from Cyrus and Matt Warren

The good part is that since I work in Microsoft, soon (after VS 2005 release I guess) we'd move to C#3.0 to dogfood it. So that means I'll not be required to wait for the super enhancements in C# for long!!!!

I thought I'd try out the features of C#3.0 and write some stuff on it. Here goes the second one (the first is already there)

Extension Methods

With extension methods you can attach additional functionalities to an existing type even if you do not have access to it. For example I can write an  extension method Print() which prints each element of any collection on a different line and then invoke it on any collection such as

List<string> first = new List<string>();

first.AddRange (new string[] {"Hello", "how"});

first.Print();

Importantly note is that even though Print() is not a member of List<> but is still called as if its a method. There are a couple of restrictions in defining the extension method Print. All of which are marked in bold in the example below

public static class Extensions

{

public static void Print<T>(this ICollection<T> col)

{

foreach(T t in col)

Console.WriteLine(t);

}

}

static void Main(string[] args)

{

List<string> first = new List<string>();

first.AddRange (new string[] {"Hello", "how"});

first.Print();

}

The method has to be a static method in a static class. The first parameter to the method has to be qualified using this and this first parameter indicates the types on which this extension method can be applied. Its important to note that this is just syntactic sugar and both the following calls are equivalent and legal.

first.Print();

Extensions.Print(first);

So whats the benefit? I think this makes code more elegant and this can be used very much like C++ STL algorithms. Lets say I write a merge algorithm that merges two collections and then I'd be able to call this merge algorithm on any collection in a very elegant way. Following is the implementation of a merge algorithm

using System;
using
System.Collections.Generic;
// Will compile only with C#3.0 complilers
namespace
ExtensionMethodDemo
{
    public static class
Extensions
    {
        public static void Merge<T>(this ICollection
<T> first, ICollection<T> second)
        {
            foreach(T t in
second)
                first.Add(t);
        }
   
}

    class Program
    {
        static void Main(string
[] args)
       
            List<string> first = new List<string
>();
            first.AddRange (
new string[] {"Hello", "how"
});

            List<string> second = new List<string
> ();
            second.AddRange (
new string[] {"are", "you", "doing"
});

            first.Merge(second);
        }
    }
}

Moreover the class libarary already ships with some standard extension methods (like standard algorithms of STL) and you can directly use them. Consider the following

int[] a = new int[] {1, 2, 2, 4, 3};

Console.WriteLine(a.Distinct().Count());

Here two of the methods Distinct and Count are used and the combined result is that we get the number of distinct elements in the array and that is 4. This is really really cool.

As a real life sample I wrote a pretty print extension method that prints the directory listing is a pretty fashion.

using System;
using System.Collections.Generic;
using System.Text;
using System.Query;
using System.IO;

namespace ExtDemo
{
   
    public static class Extensions
    {
        public
static void PrettyPrint(this
IEnumerable<FileInfo> fInfo)
        {
            ConsoleColor defColor = Console.ForegroundColor;
            string format = "{0, -17} {1,10} {2}";
            Console.ForegroundColor = ConsoleColor.Green;
            Console.WriteLine(format,
"Date", "Size (kb)", "File name");
            Console.ForegroundColor = defColor;
            foreach(FileInfo file in fInfo)
            Console.WriteLine(format, file.CreationTime.ToString(
"dd/MM/yyyy hh:mm"), (float)file.Length / 1024, file.Name);
        }
    }
    class Program
    {
        static void Main(string[] args)
       
            DirectoryInfo
dirInfo = new DirectoryInfo(@"c:\");
            dirInfo.GetFiles().PrettyPrint();
        }
    }
}

The C# 3.0 spec clearly calls out that since this is not a very discoverable feature and is somewhat misleading (very much like operator overloading) and so should be used sparingly. I think that this'll be more and more used by class libraries to implement STL like algorithms that can be run on containers.

Published Thursday, September 15, 2005 10:42 PM by abhinaba
Filed under:

Comment Notification

If you would like to receive an email when updates are made to this post, please register here

Subscribe to this post's comments using RSS

Comments

# C# 3.0: Lambda expressions. I don't like it that much

Saturday, September 17, 2005 7:43 AM by I know the answer (its 42)
This is the my third post on the series of post I am making on C#3.0 after it got declared on PDC. See...

# C# 3.0: Lambda expressions. I don't like it that much

Saturday, September 17, 2005 7:45 AM by I know the answer (its 42)
This is the my third post on the series of post I am making on C#3.0 after it got declared on PDC. See...

# C# 3.0: I love object and collection initializers

Saturday, September 17, 2005 11:36 AM by I know the answer (its 42)
This is the my fourth post in the series of posts I am making on C#3.0. See the previous posts here,...

# C# 3.0: I do not like Anonymous types

Monday, September 19, 2005 2:38 AM by I know the answer (its 42)
This is the my fifth post in the series of posts I am making on the new features in C#3.0. See the previous...

# C# 3.0: I do not like Anonymous types

Monday, September 19, 2005 2:40 AM by I know the answer (its 42)
This is the my fifth post in the series of posts I am making on the new features in C#3.0. See the previous...

# C# 3.0: I do not like Anonymous types

Monday, September 19, 2005 3:40 AM by I know the answer (its 42)
This is the my fifth post in the series of posts I am making on the new features in C#3.0. See the previous...

# C# 3.0: I do not like Anonymous types

Monday, September 19, 2005 8:56 AM by I know the answer (its 42)
This is the my fifth post in the series of posts I am making on the new features in C#3.0. See the previous...

# Make all your utility methods 'Extension methods'

Wednesday, July 26, 2006 12:39 PM by I know the answer (it's 42)
As I had previously said I love extension methods&amp;nbsp;and have started using them at multiple places...

# re: C# 3.0: I like Extension Methods

Monday, August 07, 2006 9:25 AM by print
i want to print a windoe form  on printer
whats this method?
thanks

# re: C# 3.0: I like Extension Methods

Monday, August 07, 2006 9:26 AM by print
i want to print a window form  on printer
whats this method?
thanks

# Jim Wooley search for the missing LINQ

Wednesday, September 06, 2006 11:06 AM by Atlanta .NET Regular Guys
&amp;nbsp;Jim Wooley, leader of the Atlanta Visual Basic Study Group, presented to the Atlanta C# User Group...

# Jim Wooley searches for the missing LINQ

Wednesday, September 06, 2006 11:08 AM by Atlanta .NET Regular Guys
&amp;nbsp;Jim Wooley, leader of the Atlanta Visual Basic Study Group, presented to the Atlanta C# User Group...

# re: C# 3.0: I like Extension Methods

Thursday, February 22, 2007 8:58 AM by Matthieu MEZIL

I love extension methods.

for "int[] a = new int[] {1, 2, 2, 4, 3};", you can write this with C#3.0 : "int[] a = {1, 2, 2, 4, 3};" isn't it great?

# re: C# 3.0: I like Extension Methods

Thursday, May 10, 2007 1:55 PM by Vinu

Really its an awesome thing. Its gonna be widely used. Many of us would face this problem of adding a new method to an existing class, so it will definitely be helpfull.

# re: C# 3.0: I like Extension Methods

Friday, August 03, 2007 12:09 PM by Ian Suttle

Thanks for this article.  I've included a bit more info on extension methods on my blog as well: http://www.iansuttle.com/blog/post/Extension-Methods-in-C-30.aspx

# re: C# 3.0: I like Extension Methods

Sunday, August 12, 2007 11:13 PM by Chui

Thanks. What happens when identical signatures clash?

# substr() vs String.Substring()

Sunday, November 11, 2007 7:56 PM by speak-friend.com blog

substr() vs String.Substring()

# True object oriented language

Thursday, November 22, 2007 1:33 AM by Noticias externas

Today I was spreading the goodness of Ruby and why I love it so much (and you can expect multiple posts

# True object oriented language

Thursday, November 22, 2007 7:30 AM by I know the answer (it's 42)

Today I was spreading the goodness of Ruby and why I love it so much (and you can expect multiple posts

# Cool C# 3.0 Extension Method Idea

Sunday, December 23, 2007 4:57 PM by Page Brooks

Cool C# 3.0 Extension Method Idea

Leave a Comment

(required) 
required 
(required) 
 
Page view tracker