An extension method is a feature that adds the capability of adding methods to an existing class without altering or creating a new class. They allow extending the functionality of existing types, for example add a new method to the "string" type. Now let's first see it working.
I want to add a meaningless method to a string type that will return the greetings (array of strings) to the passed string. So if I pass "ram" then it should return an array as follows.
- Hello ram
- Good Morning ram
- Good evening ram
- Good bye! ram
I also want to control my good morning, evening and bye message using flags, however the Hello message must be returned everytime.
Procedure
- Create a static class.
- Create the desired method as static in the static class.
- Include the namespace of the static class where you want to use it.
- Intellisense will list it after every string type variable.
- using System;
-
- namespace ConsoleApplication2
- {
- class Program
- {
- static void Main(string[] args)
- {
- Console.WriteLine("Enter the name");
- string name = Convert.ToString(Console.ReadLine());
- foreach(string str in name.Greeting(true,false,true))
-
- {
- Console.WriteLine(str);
- }
- Console.ReadLine();
- }
- }
-
-
- public static class NameAnything
- {
- public static string[] Greeting(this string name, bool isMorningGreeting, bool isEveningGreeting, bool isGoodByeGreeting)
- {
- return new string[] { "Hello " + name, isMorningGreeting ? "Good Morning " + name : null, isEveningGreeting ? "Good Evening " + name : null, isGoodByeGreeting ? "Good bye ! " + name : null };
- }
- }
- }
And the output:
Now let us see one more examples of adding extension methods to an existing class. Let us suppose we have our pre-built library of player classes that implement an IPlayer interface as follows.
IPlayer Interface
- namespace MyInterface
- {
- public interface IPlayer
- {
- void Play();
- }
- }
The following shows MyPlayer classes implementing IPlayer:
- using System;
- using MyInterface;
-
- namespace MyPlayers
- {
- public class Bowler : IPlayer
- {
-
- public void Play()
- {
- Console.WriteLine("Bowler play method.");
- }
- }
-
- public class Batsman : IPlayer
- {
-
- public void Play()
- {
- Console.WriteLine("Bastman play method.");
- }
- public void Speaks(string str)
- {
- Console.WriteLine("Bastman speaks method. Hi " + str);
- }
- }
- }
The Bowler class implements the Play method from an interface whereas the Batsman class defines the additional method Speaks. Over a period of time, you might have added other player classes like Fielder, WicketKeeper, ExtraPlayer, AllRounder and so on implementing only the Play method. You want to add a method "Speaks" to all the classes implementing IPlayer. You should be able to do it by adding the following code.
My extension method:
- using System;
-
- namespace MyExtensions
- {
- using MyInterface;
- public static class GiveAnyName
- {
- public static void Speaks(this IPlayer ip, string name)
- {
- Console.WriteLine("Extension speaks method : Hi " + name);
- }
-
- public static void Play(IPlayer ip)
- {
- Console.WriteLine("Play extension method.");
- }
- }
- }
Now this is how you can call the extension method.
- using System;
-
- namespace MyApplication
- {
- using MyExtensions;
- using MyPlayers;
- class Program
- {
- static void Main(string[] args)
- {
- Bowler bowler = new Bowler();
- Batsman batsman = new Batsman();
-
- bowler.Play();
- bowler.Speaks("Sunil");
-
- batsman.Play();
- batsman.Speaks("Sachin");
-
- Console.ReadLine();
- }
- }
-
- }
So there is no difference between consuming class methods and extension methods. Wait! Let us see the result.
Arrgh! The result seems a bit strange for the Bowler class. It calls an extension method whereas for Batsman it calls the method defined in the class. So why is it like that? It is because at compile time, extension methods always have a lower priority than instance methods defined in the type itself. If you are coming from a JavaScript programming background then you can quickly correlate it with a prototype property of a function. So you can't use extension methods to override the class.
Extension methods can only be brought into the scope of the namespace. If the namespace is not included, the extension method will not be available.
Though extension methods add power you are less likely to implement it. Having said so, you are definitely going to use extension methods in any real project when you use LINQ. LINQ leverages the power of extension methods to IEnumerable and IQuerable types.