Menus

Friday, December 28, 2012

LINQ in C# : How does it work? - Part II

Introduction

In the first part of How does it work in C#? article I discussed about the var, auto-implemented properties and += and -= of events in C#. In this article, I will be discussing about throwing an exception and how does it work and what is the internal mechanism for these, what is internal working mechanism of where and select clause of Enumerable class in C#.

How does it work?

In the following discussion we will see the internal working mechanism about the throw statement and where, select of Enumerable class.
throw an exceptionObject
Exception is one of the common scenarios for any application. As a result, proper exception management is one of the important tasks in application development. In here, I would like to discuss about throw statement in C#, how does throw anExceptionObject; or just throw works. I wrote a small program which will help me to explain the details. The task of this program is simple, it will raise an exception and throw it,
namespace TestHarnessPart2
{
    using System;
    class Program
    {
        static void Main(string[] args)
        {
            try
            {
                Person person = new Person();
            }
            catch (Exception exceptionObject)
            {
                throw;
            }
        }
    }
    public class Person
    {
        public Person()
        {
            throw new Exception("Exception from Person.");
        }
    }
}
The above code catch the exception and just throw it with out passing any explicit exception object.I created another version of this above code for example,
namespace TestHarnessPart2
{
    using System;
    class Program
    {
        static void Main(string[] args)
        {
            try
            {
                Person person = new Person();
            }
            catch (Exception exceptionObject)
            {
                throw exceptionObject;
            }
        }
    }
    public class Person
    {
        public Person()
        {
            throw new Exception("Exception from Person.");
        }
    }
}
The above code will create a Person object and if any exception occurred during this creation it will catch that exception and from the catch block it throws the catched exception which is throw exceptionObject;. Now if we see the stack trace of those above code we will find out there is difference, stack trace for first version of the code is as below,

HowitworksCSharpTwo/StackTraceThrow.PNG

Fig: Stack trace of the first version of the code.
And stack trace of the second version of the code,

HowitworksCSharpTwo/StackTraceThrowException.PNG

Fig: Stack trace of the second version of the code
From the above two images we can see the details of the stack trace is different.Now the question is how does it happens, to get the answer we will get help of ILDasm program, grab the exe of TestHarnessPart2 from the bin folder and drop into the ILDasm program , for the first version of the code we will see something like below,
HowitworksCSharpTwo/ILThrow.PNG
Fig :IL code for using just throw in the catch block.
From the above image we can see exceptionObject has been defined as local variable using .locals init [1] but in the catch block compiler change the throw statement into
catch [mscorlib]System.Exception 
{
   IL_000b:  stloc.1
   IL_000c:  nop
   IL_000d:  rethrow
}  // end handler
rethrow, which means compiler does not change the original stack trace of the exception object it is re- throwing the existing one, where as if we look into the following image for the second version of the above C# code,
HowitworksCSharpTwo/ILThrowExceptionObject.PNG
Fig: IL code for using just throw excetpionObject in the catch block.
We can see exceptionObject has been defined as local variable as well, using the same way for the first version of the code for example, .locals init [1]. But in the catch block it is doing totally different stuffs compare to first version of the above code. In the catch block compiler load location of 1( ldloc.1) which is the exceptionObject
  catch [mscorlib]System.Exception
  {
    IL_000b:  stloc.1
    IL_000c:  nop
    IL_000d:  ldloc.1
    IL_000e:  throw
  }  // end handler
and throw that one. As a result, this exceptionObject will not hold all the stack trace raised earlier except the stack trace from this current state. Now the last bit of the puzzle is, what actually throw and rethrow statement does? From the Partition III CIL.doc retrieved from ECMA C# and Common Language Infrastructure Standards we can see what actually throw and rethrow does,
IL Instruction Description
throw Throw an exception. The throw instruction throws the exception object (type O) on the stack and empties the stack. So in relation to the second version of the code block it will be,
[1] class [mscorlib]System.Exception 
exceptionObject
rethrow Rethrow the current exception. The rethrow instruction is only permitted within the body of a catch handler. It throws the same exception that was caught by this handler. A rethrow does not change the stack trace in the object.

So it is clear that throw exceptionObject override the stack trace where as, just throw statement does not override the stack trace.
Where and Select of Enumerable
Before we start discussing about Where and Select, just have a quick look of the where and select clause’s signature,
HowitworksCSharpTwo/WhereSignature.PNG
Fig: Signature of the Where clause
HowitworksCSharpTwo/SelectSignature.PNG
Fig: Signature of the Select clause
Where and Select is two extension methods of Enumerable class in .Net. Following sections will discuss about the internal of Where and Select, how does it work. Before, we go ahead just bit of heads up about Func in .Net. According to MSDN, we can use this delegate to represent a method that can be passed as a parameter without explicitly declaring a custom delegate. The encapsulated method must correspond to the method signature that is defined by this delegate. A simple example of Func below,
namespace TestHarnessPart2
{
    using System;
    public class ExampleOfFunc
    {
        public int TestFunc(string dataToCheck, Func<string,> getLength)
        {
            return getLength(dataToCheck);
        }
    }
}
and to test the above code,
private static void TestFuncExample()
{
    ExampleOfFunc exampleOfFunc = new ExampleOfFunc();
    Console.WriteLine(exampleOfFunc.TestFunc("Example of Func", (dataToTest) => dataToTest.Length));
}
So from the above code we can see TestFunc method accepting a Func as parameter and execute it just by doing return getLength(dataToCheck);, from the caller of this method is actually passing an anonymous method block for the Func parameter. Through out the entire discussion about where and select we will find this concept used many places,
Before we go ahead I like to show a bit of code created to explain the where and select statement,
namespace TestHarnessPart2
{
    using System.Collections.Generic;
    using System.Linq;
    class WhereSelect
    {
        List<string> bookList = new List<string>() { "Einstein: His Life and Universe", "Ideas And Opinions"
"The World As I See It " };
        public IEnumerable<string> GetBookListWhichLengthIsGreaterThan(int lengthOfTheBookName)
        {
            //return bookList.Where(book => book.Length == lengthOfTheBookName).Select(book => book);
            return bookList.Where(book =>
            {
                var currentBook = book;
                return book.Length > lengthOfTheBookName;
            }).Select(book =>
            {
                var currentBook = book;
                return book;
            });
        }
    }
}
The above code is not doing much rather check the booklist whether it has book which name length is greater than given length (lengthOfTheBookName). Now we will try to find out bit of internal working mechanism of Where and Select clause, where and select clause is defined in the Enumerable class and internal of the where clause is as below,
HowitworksCSharpTwo/WhereInternal.PNG
Fig: Where internal
From the above image we see Where method is calling another internal private class named WhereListIterator<T> which is doing all the work for us which is filter the booklist List based on the condition provided and return output.
private class WhereListIterator<tsource> : Enumerable.Iterator<tsource>
{
      public override bool MoveNext()
      {
        // most of the code has been removed for simplicity
        while (this.enumerator.MoveNext())
        {
          TSource current = this.enumerator.Current;
          if (this.predicate(current))
          {
            base.current = current;
            return true;
          }
        }
      }
}
From the above code we can see this.predicate(current)) line of code is actually executing the Func or anonymous method block in this case, <GetBookListWhichLengthIsGreaterThan>b__0 method. On the other hand, select clause is working like below,
HowitworksCSharpTwo/SelectInternal.PNG
Fig: Select internal
Also, from the above image we can see that there is one selector which is actually <GetBookListWhichLengthIsGreaterThan>b__1 method to select the item from the list. Now need to find out where is this <GetBookListWhichLengthIsGreaterThan>b__1 and
<GetBookListWhichLengthIsGreaterThan>b__0
coming from? Please have a look image below, from the following image we can there is two method named <GetBookListWhichLengthIsGreaterThan>b__1 used for selector and
<GetBookListWhichLengthIsGreaterThan>b__0 used for predicate of the where clause.
HowitworksCSharpTwo/OutputOfTheWhereSelectWithPredicates.PNG
Fig: The output of WhereSelect test
Where and Select clause is using those two methods for doing the operation. Bit of more investigation to find out about it. Now we need the help of .Net Reflector and ILDasm. First grab the TestHarnessPart2.exe from the bin folder and drop into .Net Reflector, then we will find out following interesting stuff, a class <>c__DisplayClass3 with following details,
[CompilerGenerated]
private sealed class <>c__DisplayClass3
{
    // Fields
    public int lengthOfTheBookName;
    // Methods
    public bool <GetBookListWhichLengthIsGreaterThan><getbooklistwhichlengthisgreaterthan>b__0(string book)
    {
        string currentBook = book;
        return (book.Length > this.lengthOfTheBookName);
    }
}
From the class we can see a method named <GetBookListWhichLengthIsGreaterThan>b__0 which is actually containing the filtering condition we defined in the where clause,
{
     var currentBook = book;
     return book.Length > lengthOfTheBookName;
}
And also there is also another method (outside of <>c__DisplayClass3 class) named <GetBookListWhichLengthIsGreaterThan>b__1
[CompilerGenerated]
private static string <GetbookListWhichLengthIsGreaterThan><getbooklistwhichlengthisgreaterthan>b__1(string book)
{
    string CS$<>8__locals4 = book;
    return book;
}
Which is actually containing the statement we defined for the select clause as below,
{
     var currentBook = book;
     return book;
}
Now to prove the above stuff, we will look at the IL code retrieved from ILDasm(also grab the TestHarnessPart2.exe from the bin folder and drop into ILDasm program) for the above C# code,

HowitworksCSharpTwo/ILCodeForWhereSelect.PNG
Fig: IL code of the GetBookListWhichLengthIsGreaterThan method
From the above image we can see where clause is using <GetBookListWhichLengthIsGreaterThan>b__0 method of <>c__DisplayClass3 class and select clause is using <GetBookListWhichLengthIsGreaterThan>b__1 method. So it is clear now how does it work.
Limitation
  • There are no discussions about Query Expression and Lambda Expression.

LINQ in C# : How does it Work? - Part I

Introduction

The C# language of the .NET(MSDN), has many features such as var to declare variable, implement the properties automatically and many more which makes life of a programmer easier. On the other hand, this abstraction creates a bit of confusion such as how does it work, how .Net implemented those stuffs in behind the scene. In this article, I will try to find out few of those stuff for example, var, Auto-Implemented properties and += or -= syntax used in Events.

How does it work?

In the following discussion, we will see how does var, auto-implemented properties and += and -= of Events work
var and details
In C#, it is possible to declare variable in few ways, implicit type declaration using var keyword is one of those. For example, it is possible to use var totalSalary =0; instead of int totalSalary =0;. As MSDN article suggested var is strongly typed but compiler determined the types. To explore it a bit more, I created a small class,
namespace TestHarness
{
    public class VarExplorer
    {
        public Book ExploreVar()
        {
            var myBook = new Book() { Name = "What is out there?" };
            myBook.Name = "What is out there?";
            return myBook;
        }
    }
    public class Book
    {
        public string Name { get; set; }
    }
}
The above class is not doing much rather initialising an instance of type Book which contains a method named ExplorerVar. This method has variable declared using var. In the design time or coding or while writing code in the IDE, hover the mouse just above the keyword var then the compiler will determine the types of variable myBook. Please have a look the image below,

How_does_work_in_CSharp/VarAtDesignTime.PNG

Fig: var at design time
So it is clear that compiler determine the types at design time. Another question is what is happening at runtime? To test, I compiled the TestHarness project and grab the TestHarness.exe from the bin folder and drop into .Net Reflector program, using the help .Net Reflector the code I found out for ExploreVar method is as below,
public Book ExploreVar() 
{
    Book <>g__initLocal0 = new Book {

        Name = "What is out there?"

    };
    Book myBook = <>g__initLocal0;
    myBook.Name = "What is out there?";
    return myBook; 
}
The above code clearly shows that compiler replace var keyword with appropriate type while building project as exe. From the above discussion, it is clear how does var work in C#.
Auto-Implemented Properties
In C# class declaration is pretty easy we declare a class using following syntax,
public class Book 
{
       private string name;
       public string Name  
       {
            get {
                return name;
            }
            set {
                name = value;
            }
       }
}
It is really simple but from C# 3.0 it is more easier. We can declare Book class as below,
public class Book
{ 

   public string Name { get; set; }

}
Now the question is what is the difference between that syntax used to declare a class. In reality there is nothing except compiler doing all the work for us. A Bit of background of class, the concept of the Encapsulation has been implemented in different way. First declaration of Book class, the encapsulation has done by introducing Properties which actually equivalent to Get and Set method. So it is not possible to directly access the private members of the class unless there is a Public Properties or Get/Set method.
Now for the second syntax of the Book declaration, compiler is doing all this encapsulation on behalf of a programmer. When decompile second version of Book using .Net Reflector, Compiler itself generates get and set methods for Name property and declare a variable name <Name>k__BackingField ( in here <Name> is actuall property name defined in Book class ),
So whole decompiled code for Name is as below,
private string <name>k__BackingField;

public void set_Name(string value)
{
    this.<name>k__BackingField = value;
}

public string get_Name()
{
    return this.<name>k__BackingField;
}
From the above discussion clear that how compiler handle auto implemented properties. A bit more investigation at runtime, I created following code snippet to test the auto implemented properties stuff at run time,
    using System.Collections.Generic;
    using System.Linq;
    using System.Reflection;

    public class AutoImplementatedProperties
    {
        public IEnumerable<string> ExploreMembers(Person personObject)
        {
        return personObject.GetType().GetMembers().ToList<memberinfo>().Select(memberInfo => 
memberInfo.Name);
        }

        public IEnumerable<string> ExplorePrivateFields(Person personObject)
        {
            return personObject.GetType().GetFields(BindingFlags.NonPublic |
 BindingFlags.Instance).Select(fieldInfo => string.Format("{0,40}-->{1,20}", fieldInfo.Name, 
fieldInfo.GetValue(personObject).ToString()));
        }
        public Person CreateATestObject()
        {
            Person personObject = new Person()
            {
                Name = "M",
                Profession = "Coding"
            };
            return personObject;
        }
    }
    public class Person
    {
        public string Name { get; set; }
        public string Profession { get; set; }
    }
}
In the above class, ExploreMembers method will explore all the members of Person object and ExplorePrivateFields will explore all the private fields including their value of Person object. If we run the ExplorePrivateFields method then we can see it will display,
How_does_work_in_CSharp/OutputOfAutoImplementedProperties.PNG
Fig: Auto-implemented properties test result.
Above output and now if compare with Person instantiation code below,
public Person CreateATestObject()
{
    Person personObject = new Person()
    {
        Name = "M",
        Profession = "Coding"
    };
    return personObject;
}
It is clear that How C# store Name and Profession property values at runtime.
+= and -= in Events
The definition of Event has been taken from MSDN. An event in C# is a way for a class to provide notifications to clients of that class when some interesting thing happens to an object.
The main point of this discussion is to discuss about, += (add) or -= (remove) syntax and how does it relates to the Event and delegate and also how does it work? Actually, the compiler translate += or -= into add or remove method in Layman’s terms. So to test the concept, I created small class (which is doing pretty much nothing),
public class LogIt
{
    public delegate void LogHandler(string message);
    public event LogHandler Log;
    public Delegate[] GetList()
    {
        return Log.GetInvocationList();
    }
}
So the above class has a delegate name LogHandler and event named Log of type LogHandler. The consumer of this class is as below,
public class AddRemoveHandlerOfEvent
{
    public LogIt InitialiseLogIt()
    {
        LogIt logItObject = new LogIt();
        logItObject.Log += new LogIt.LogHandler(Logger1);
        logItObject.Log += new LogIt.LogHandler(Logger2);
        logItObject.Log += new LogIt.LogHandler(Logger3);
        return logItObject;
    }

    public void Logger1(string s)
    {
        Console.WriteLine(s);
    }

    public void Logger2(string s)
    {
        Console.WriteLine(s);
    }

    public void Logger3(string s)
    {
        Console.WriteLine(s);
    }
}
So from the above consumer class we can see few methods such as Logger1, Logger2, Logger3 has been added to the Log of LogIt object. Now the question is where does these methods information stored or how does it works while use += or -= syntax. To answer the question again need to get help of .Net reflector. When we reflect the code we can see following code has generated by compiler for += or -=,
public class LogIt
{
    // Nested Types
    public delegate void LogHandler(string message);
    // Fields
    private LogHandler Log;
    // Events
    public event LogHandler Log
    {
        add
        {
            LogHandler handler2;
            LogHandler log = this.Log;
            do
            {
                handler2 = log;
                LogHandler handler3 = (LogHandler) Delegate.Combine(handler2, value);
                log = Interlocked.CompareExchange<loghandler>(ref this.Log, handler3, handler2);
            }
            while (log != handler2);
        }
        remove
        {
            LogHandler handler2;
            LogHandler log = this.Log;
            do
            {
                handler2 = log;
                LogHandler handler3 = (LogHandler) Delegate.Remove(handler2, value);
                log = Interlocked.CompareExchange<loghandler>(ref this.Log, handler3, handler2);
            }
            while (log != handler2);
        }
    }
    // Methods
    public Delegate[] GetList()
    {
        return this.Log.GetInvocationList();
    }
}
There are two new stuffs which is add and remove, need to explore now does add and remove works, from add block one line of code give us all the clue which is,
LogHandler handler3 = (LogHandler) Delegate.Combine(handler2, value);
and if we dig bit more with Combine method, we will find out something like below,
public static Delegate Combine(Delegate a, Delegate b)
{
    if (a == null)
    {
      return b;
    }
    return a.CombineImpl(b);
}
The code block is from the Delegate class and also CombineImpl method called from Combine method is defined in the MulticastDelegate class.
The MulticastDelegate holds two variable
private IntPtr _invocationCount; 
private object _invocationList; 

and this _invocationList is the main object which holds all the method signature assigned using += syntax. From the below images we can see how does _ invocationList used to store all the method signature as method pointer(IntPtr) How_does_work_in_CSharp/ObjectAsInvocationList.PNG
Fig: _innvocationList of MulticastDelegate class

How_does_work_in_CSharp/ObjectHoldInvocationList.PNG
Fig: objArray at runtime.

How_does_work_in_CSharp/EventAtRuntimeResized.PNG
Fig: In depth view of the objArray to find out method information from _ innvocationList
To get a clear view of this, I created a small test program to test, how .Net store all the method inside the _invocationList. If we see the below code block of the CombineImpl method,
public IEnumerable<string> GetInitialMethodPointer()
{
    return GetType().GetMethods().Select(methodInfo => string.Format("{0,40}-->{1,20}",
 methodInfo.Name,methodInfo.MethodHandle.Value.ToString()));
}

public IEnumerable<string> GetInvocationListFrom(LogIt logItObject)
{
    return logItObject.GetList().Select(delegateObject => string.Format("{0,40}-->{1,20}",
 delegateObject.Method.Name,
 delegateObject.Method.MethodHandle.Value.ToString()));
}
</string></string>
We can see, GetInitialMethodPointer method will show the initial methods pointer for Logger1, Logger2 and Logger3 and GetInvocationListFrom method will show what does _invocationList contains after using += operation to add method signneture. From the image below, it is clear that _invocationList contains exactly the same method pointer value we get from GetInitialMethodPointer.
How_does_work_in_CSharp/EventsOutput.PNG
Fig: Output of the method pointer store into _ innvocationList

The implementation of -= is also a bit of nice stuff to dissect. Following Call Stack will show how the remove calls from consumer code to all the way back into Delegate class to update _ invocationList list,
How_does_work_in_CSharp/RemoveEvents.PNG


Fig: Call Stack of Delete Operation


And if we look into the RemoveImpl method code then we can see it called another method named DeleteFromInvocationList as below,

  How_does_work_in_CSharp/RemoveInitialCode.PNG

Fig: Inside of the RemoveImpl method


And code inside DeleteFromInvocationList will eventually update the _ invocationList list to update the current method signature after remove. Please see the following image,
How_does_work_in_CSharp/InsideOfDeleteOperation.PNG

Fig: Inside of DeleteFromInvocationList
So from the above discussion we have pretty good picture of how += and -= works for Events and Delegate.
If you interested detail about other features of the C# language, Expert C# 5.0 with the .NET 4.5 Framework might be useful.

LINQ in C# : How does it work in C#? - Part III

LINQ basics

In .NET any data structure which is derived from the IEnumerable<T> interface of the System.Collections.Generic namespace of the mscorlib.dll (this assembly is located in C:\Windows\Microsoft.NET\Frameworkv4.0.30319 but depends on the installation of the VS) assembly is able to access all the extension methods defined in the Enumerable class of the System.Linq namespace of the System.Core.dll assembly in the .NET Framework (see more about LINQ). This Enumerable class is a static non inheritable class defined in the System.Linq namespace of the System.Core.dll assembly(C:\Windows\Microsoft.Net\assembly\GAC_MSIL\System.Core\v4.0_4.0.0.0__b77a5c561934e089\System.Core.dll but depends on the installation of VS). The definition of the Enumerbale class is as below:
.class public abstract auto ansi sealed beforefieldinit
System.Linq.Enumerable extends [mscorlib]System.Object
    Note: The figure shows the Enumerable class decompiled using the ILDasm.exe program,

    Fig: Enumerable class in ILDasm.exe program.
The static Enumerable class is a container of the different extension methods for the IEnumerable<T> interface, for example,
public static bool Contains<TSource>(
    this IEnumerable<TSource> source, TSource value)
{ /* code removed*/}
public static int Count<TSource>(
    this IEnumerable<TSource> source) 
{ /* code removed*/}
public static IEnumerable<TSource> Distinct<TSource>(
    this IEnumerable<TSource> source, IEqualityComparer<TSource> comparer) 
{ /* code removed*/}
// and many more
Please read more about extension methods here Or Chapter 04 of the Expert C# 5.0 with .NET Framework 4.5 book.

Extension method - behind the scene - Now do bit of interesting work, in this research I use ILDasm(C:\Program Files\Microsoft SDKs\Windows\v7.0A\bin\NETFX 4.0 Tools\ildasm.exe but this is for my installed VS) tool which comes as part of the VS installation. I use the same C# code as OP provided except change the class name Exte to ExtensionMethodClass. I build the program and grab the exe of the program in this case it is ConsoleApplication24.exe (as I put the code in the console app which is called ConsoleApplication24.) into the ILDasm program and ILDasm generate following IL code for the ExtensionMethodClass class in here we define the extension method.
.class public abstract auto ansi sealed beforefieldinit ExtensionMethodClass
    extends [mscorlib]System.Object
{
    .custom instance void [System.Core]System.Runtime.CompilerServices.ExtensionAttribute::.ctor()
    .method public hidebysig static string GetFirstThreeCh(string str) cil managed
    {
        .custom instance void [System.Core]System.Runtime.CompilerServices.ExtensionAttribute::.ctor()
        .maxstack 3
        .locals init (
            [0] string str2,
            [1] bool flag)
        //removed all the code for clearity
    }

}
If we look into the IL code above, we can see:
  • ExtensionMethodClass class has been define as abstract and sealed.
  • Inside this class GetFirstThreeCh method has been compiled as static public method which has string type parameter. Note that in here there is no this which we define in the C# code in the GetFirstThreeCh method.
  • So it is clear more this IL code that extension method has been define as same as static method.
Let’s see the usage of this GetFirstThreeCh extension method from the Main method which will show us the calling convention of the extension method in underneath. I extracted the following IL code from the program class of the ConsoleApplication24.exe program using the ILdasm:
.method private hidebysig static void Main(string[] args) cil managed
{
    .entrypoint
    .maxstack 1
    .locals init (
        [0] string str)
    L_0000: nop 
    L_0001: ldstr "my new String"
    L_0006: stloc.0 
    L_0007: ldloc.0 
    L_0008: call string ConsoleApplication24.ExtensionMethodClass::GetFirstThreeCh(string)
    L_000d: stloc.0 
    L_000e: ret 
}
From the above IL code in L_0008 label we can see that GetFirstThreeCh method has been call as same as CLR call static method.To test this I created a small static class with a static method as below:
namespace ConsoleApplication24
{
    class Program
    {
        static void Main(string[] args)
        {
              TestStaticMethod.TestMethod();
        }
    }    

    public class TestStaticMethod 
    {
        public static void TestMethod() 
        {
          /*Code has been removed*/   
        }
    }
}
After building this new program I decompiled using ILDasm program to generate the IL code which is as below:
.method private hidebysig static void Main(string[] args) cil managed
{
    .entrypoint
    .maxstack 8
    L_0000: nop 
    L_0001: call void ConsoleApplication24.TestStaticMethod::TestMethod()
    L_0006: nop 
    L_0007: ret 
}
So we can see that how does CLR handle the extension method in behind the scene.
And Iterators in here. A complete list of extension methods defined in the Enumerable class is in here.
Let’s see how these extension methods work internally.

Extension Methods

Where and Select

Where and Select are two important extension methods of the IEnumerable<TSource> interface defined in the Enumerable class of the System.Core.dll assembly.
public static IEnumerable<TSource> Where<TSource>(this IEnumerable<TSource> source, Func<TSource, bool> predicate)
public static IEnumerable<TSource> Where<TSource>(this IEnumerable<TSource> source, Func<TSource, int, bool> predicate)
So any data structure derived from IEnumerable<TSource> interface is be able to access these two extension methods over that data structure such as List<T> class. List<T> class implemented the IEnumerable<T> interface as the signature of the List<T> class shows as below,
public class List<T> : IList<T>, ICollection<T>, IEnumerable<T>, IList, ICollection, IEnumerable
For more information please see Where and Select. Let’s see an example in here where the Where and Select extension methods have been used.
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<string> numbers = new List<string>() 
            { 
                "One", "Two", "Three", "Four", 
                "Five", "Six", "Seven" 
            };

            var numbersLengthThree =
                numbers.Where(x => x.Length == 3).Select(x => x).ToList();

            numbersLengthThree.ForEach(x => Console.WriteLine(x));
        }
    }
}
This code will create a list of string objects and store into a List<string> object, numbers. The above program will find out those items from the numbers whose total number of characters is equal to 3 and store the result into a new list, numbersLengthThree. Finally, display the number on the console. This program will produce the following output,
One
Two
Six
Let’s do bit of research to find out how does it work. The most important code from the above example is numbers.Where(x => x.Length == 3).Select(x => x).ToList(). Following diagram will explain the entire process of this execution.

Fig: How does Where and Select extension methods work.
From the above diagram we can see that the CLR passed the numbers list as input to the Where method along with the instance of the MulticastDelegate which holds the information about the <Main>b_1 method (created from anonymous method (x=>x.Length == 3) ). From the Where method it will return instance of the WhereListIterator<string> iterator which will then be used to pass as input parameter to the Select clause along with another instance of the MulticastDelegate class which will hold the information about the method <Main>b_2 (created from anonymous method (x=>x)). The Select method will instantiate the relevant Iterator based on the input. In this circumstance, it will be WhereSelectListIterator<string,string> iterator. This will be passed as input parameter to the ToList() method which will finally process the original list by iterating through to get the new list based on the filtering criteria. In depth of the execution will be as below,
Step 1: In the compile time, compiler will create a method <Main>b_1 using anonymous method provided for the Where methods i.e. for x => x.Length == 3.
    Note: I decompiled the executable file produced by the above program using the ILDasm.exe (C:\Program Files\Microsoft SDKs\Windows\v7.0A\bin\NETFX 4.0 Tools\ILDasm.exe depending on the VS installation) program and find out the generated method <Main>b_1 for x => x.Length == 3 code is as below,
    .method private hidebysig static bool <Main>b__1(string x) cil managed
    {
        .maxstack 2
        .locals init (
            [0] bool CS$1$0000)
        L_0000: ldarg.0 
        L_0001: callvirt instance int32 [mscorlib]System.String::get_Length()
        L_0006: ldc.i4.3 
        L_0007: ceq 
        L_0009: stloc.0 
        L_000a: br.s L_000c
        L_000c: ldloc.0 
        L_000d: ret 
    }
    Or the equivalent C# code is as below,
    private static bool <Main>b__1(string x)
    {
        return (x.Length == 3);
    }
The CLR will create an instance of the MulticastDelegate class using the method <Main>b_1 and store this method information into the MulticastDelegate instance and continue the operation.
Step 2: The CLR will continue the execution and goes to the Where<TSource>(this IEnumerable<TSource> source, Func predicate) method of the Enumerable class with the original list numbers and instance of MulticastDelegate (created in Step 1) as input to the Where method. Based on the source type of the numbers object, Where method will return the appropriate iterator instance as output. For example, based on the above example code it will return WhereListIterator<TSource> iterator which will contain the original list as source and <Main> b_1 as predicate inside it.
    Note: Complete list of iterator’s class can be found in the System.Core.dll assembly as below,

    Fig: Iterator classes used in the Enumerable clss of the System.Core.dll assembly.
The CLR will use WhereListIterator<TSource> to pass as parameter to the Select clause as input.
Step 3: In the compile time the compiler also created another method using anonymous method code (x=>x) which is <Main>b_2,
    NOTE: the contents of the <Main>b_2 method extracted via the ILDasm.exe program from the executable of the above example program,
    .method private hidebysig static string <Main>b__2(string x) cil managed
    {
        .custom instance void [mscorlib]System.Runtime.CompilerServices.CompilerGeneratedAttribute::.ctor()
        .maxstack 1
        .locals init (
            [0] string CS$1$0000)
        L_0000: ldarg.0 
        L_0001: stloc.0 
        L_0002: br.s L_0004
        L_0004: ldloc.0 
        L_0005: ret 
    }
    Or the equivalent C# code,
    private static string <Main>b__2(string x)
    {
        return x;
    }
The CLR will use this as input parameter to the MulticastDelegateclass and create another instance of the MulticastDelegate type. It will then use the iterator instantiated from the Step 2 and delegate instance in this step as input for the Select clause and move the execution to the Select method.
Step 4: In the Select method of the Enumerable class CLR will instantiate the relevant iterator based on the input of the Enumerable object and the selector delegate. For the above example, it will return an instance of the WhereSelectListIteratoriterator. This iterator will contain the original list, the predicate delegate which hold the anonymous method <Main>b_1 and the selector delegate which will contain the anonymous method b_2 inside it.
Step 5: The CLR pass this WhereSelectListIterator<string,string> iterator instance to the ToList() method as the input parameter. In the ToList() method CLR will create an instance of List<TSource> type by passing the WhereSelectListIterator<string,string> iterator as input to it.
Step 6: In the constructor of the List<TSource> class CLR will copy the list provided as input into a new list and iterate through the enumerator of the iterator (WhereSelectListIterator<string,string> ) over this new list. This will make sure original list does not alter and add the result into a dynamic array _items inside the List object. This list object will be returned as a result for the original list based on the filtering criteria. The approximate code for that is as below,
public List(IEnumerable<T> collection)
{
    ICollection<T> is2 = collection as ICollection<T>;
    if (is2 != null)
    {
    int count = is2.Count;
    this._items = new T[count];
    is2.CopyTo(this._items, 0);
    this._size = count;
    }
    else
    {
    this._size = 0;
    this._items = new T[4];
    using (IEnumerator<T> enumerator = collection.GetEnumerator())
    {
        while (enumerator.MoveNext())
        {
        this.Add(enumerator.Current);
        }
    }
    }
}

All

This extension method determines whether all elements of a sequence satisfy a condition, if every element of the source sequence passes the condition in the specified predicate, or if the sequence is empty return true; otherwise, false.
The signature of this extension method is as below,
public static bool All<TSource>(this IEnumerable<TSource> source, Func<TSource, bool> predicate)
This extension method used to determine whether a sequence of items meet a condition i.e. Each of the items in the sequence will be evaluated against the predicate. In the following program, I created an instance of the List<string> numbers which contains One, Two, Three and so on as items. Following program will find out whether the items of this sequence have at least three characters.
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<string> numbers = new List<string>() 
            { 
                "One", "Two", "Three", "Four", 
                "Five", "Six", "Seven" 
            };

            if (numbers.All<string>(x => x.Length >= 3))
                Console.WriteLine("All numbers have at least three characters.");
        }
    }
}
The above program will produce following output,
All numbers have at least three characters.
Because the extension method All will match the condition specified in the predicate whether it is valid for the item from the sequence or not. So it will be working as below,

Fig: All extension method working details.
From the above diagram we can see that the CLR will pass the numbers list as input to the extension method All along with the instance of the MulticastDelegate class created using the anonymous method (x=>x.Length >= 3) code. In the All method CLR will process the list to find out whether each of the items from the list meets the condition via the provided predicate.
The CLR will execute the extension method All as below,
Step 1: The compiler will construct a method <Main>b_1 using the anonymous method (x => x.Length >= 3) . The CLR will pass this <Main>b_1 method into the MulticastDelegate class to instantiate an instance of it. The CLR will pass the original list and the instance of the MulticastDelegate class created in this step as input to the extension method All of the Enumerable class.
Step 2: The All extension method will loop through the list and try to find out whether any element in the sequence does not meet the condition and return false otherwise a true value as a result of the operation. The approximate code for this logic is as be as below,
public static bool All<TSource>(this IEnumerable<TSource> source, Func<TSource, bool> predicate)
{
    foreach (TSource local in source)
    {
    if (!predicate(local))
    {
        return false;
    }
    }
    return true;
}
The C# method has been derived from the following IL code which has been generated by ILDasm.exe program for the Enumerable class of the System.Core.dll assembly,
.method public hidebysig static bool All<TSource>(class [mscorlib]System.Collections.Generic.IEnumerable`1<!!TSource> source, 
        class [mscorlib]System.Func`2<!!TSource, bool> predicate) cil managed
{
    .custom instance void System.Runtime.CompilerServices.ExtensionAttribute::.ctor()
    .maxstack 2
    .locals init (
        [0] !!TSource local,
        [1] bool flag,
        [2] class [mscorlib]System.Collections.Generic.IEnumerator`1<!!TSource> enumerator)
    L_001c: ldarg.0 
    L_001d: callvirt instance class [mscorlib]System.Collections.Generic.IEnumerator`1<!0> 
            [mscorlib]System.Collections.Generic.IEnumerable`1<!!TSource>::GetEnumerator()
    L_0022: stloc.2 
    L_0023: br.s L_0039
    L_0025: ldloc.2 
    L_0026: callvirt instance !0 [mscorlib]System.Collections.Generic.IEnumerator`1<!!TSource>::get_Current()
    L_002b: stloc.0 
    L_002c: ldarg.1 
    L_002d: ldloc.0 
    L_002e: callvirt instance !1 [mscorlib]System.Func`2<!!TSource, bool>::Invoke(!0)
    L_0033: brtrue.s L_0039
    L_0035: ldc.i4.0 
    L_0036: stloc.1 
    L_0037: leave.s L_004f
    L_0039: ldloc.2 
    L_003a: callvirt instance bool [mscorlib]System.Collections.IEnumerator::MoveNext()
    L_003f: brtrue.s L_0025
    L_0041: leave.s L_004d
    L_0043: ldloc.2 
    L_0044: brfalse.s L_004c
    L_0046: ldloc.2 
    L_0047: callvirt instance void [mscorlib]System.IDisposable::Dispose()
    L_004c: endfinally 
    L_004d: ldc.i4.1 
    L_004e: ret 
    L_004f: ldloc.1 
    L_0050: ret 
    .try L_0023 to L_0043 finally handler L_0043 to L_004d
}

Any

This extension method determines whether any element of a sequence exists or satisfies a condition provided as predicate.
The method signature for this extension method is as be as below,
public static bool Any<TSource>(this IEnumerable<TSource> source)
public static bool Any<TSource>(this IEnumerable<TSource> source, Func<TSource, bool> predicate)
The above two extension methods will do the following
  • First version of the Any extension method will find out whether the sequence of items contains any element in it or not.
  • Second version of the Any extension method will find out is there any element in the sequence which match the criteria provided in the predicate.
I wrote a small program to explain the working details of those two versions of extension methods from the Enumerable class.
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<string> numbers = new List<string>() 
            { 
                "One", "Two", "Three", "Four", 
                "Five", "Six", "Seven" 
            };

            if (numbers.Any<string>())
                Console.WriteLine("The sequence contains item.");

            if (numbers.Any<string>(x => x.Length >= 3))
                Console.WriteLine("The sequence contains at least a item which has three or more characters");

        }
    }
}
The above program will produce the following output,
The sequence contains item.
The sequence contains at least a item which has three or more characters
When the CLR find out the first version of the Any extension method it will execute following steps to perform the operation,
Step 1: The CLR will send the original sequence or the list in this case numbers to the Any<TSource>(this IEnumerable<TSource> source) extension method as input.
Step 2: This method will loop through the list numbers via the Enumerator object return from the list numbers and check whether the enumerator return a true value while calling the MoveNext() method of it and returns true otherwise false i.e. the sequence does not have any element in it.
The approximate code for the Any extension method is as below,
public static bool Any<TSource>(this IEnumerable<TSource> source)
{
    using (IEnumerator<TSource> enumerator = source.GetEnumerator())
    {
    if (enumerator.MoveNext())
    {
        return true;
    }
    }
    return false;
}
For the second version of the Any extension method CLR will do the following steps to execute,
Step 1: The compiler will construct a method <Main>b_1 using the anonymous method (x => x.Length >= 3) . The CLR will pass this <Main>b_1 method to the MulticastDelegate class to instantiate an instance of it and pass this MulticastDelegate instance as predicate along with the original list to the Any extension method.
Step 2: Inside the Any extension method CLR will loop through the list to execute the predicate using each item as input to the predicate. If the predicate return true of first iteration it will return true otherwise it will continue until find a match or not. The approximate code for the,
public static bool Any<TSource>(this IEnumerable<TSource> source, Func<TSource, bool> predicate)
{
    foreach (TSource local in source)
    {
    if (predicate(local))
    {
        return true;
    }
    }
    return false;
}

Average

The Average extension method calculates the average of a sequence of numeric values.
The method signature of these extension methods are below,
public static double Average(this IEnumerable<int> source)
public static decimal Average<TSource>(this IEnumerable<TSource> source, Func<TSource, decimal> selector)
An example of the Average extension method is as below,
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<int> numbers = new List<int>() 
            { 
                1,2,3,4,5,6,7,8,9,10
            };

            Console.WriteLine("Average of the numbers :{0}", numbers.Average());

            Console.WriteLine("Average of the original numbers x2 :{0}", 
                              numbers.Average((x => x * 2)));

        }
    }
}
The above program will produce the following output,
Average of the numbers :5.5
Average of the original numbers x2 :11
So when the CLR will find out the first version of the Average method as in the above program, it will do the following steps to perform the operation,
Step 1: The CLR will pass the original list in this case numbers as input to the Average method.
Step 2: The Average method will loop through the list and perform the average operation for the given list. The approximate code is as below,
public static double Average(this IEnumerable<int> source)
{
    long num = 0L;
    long num2 = 0L;
    foreach (int num3 in source)
    {
    num += num3;
    num2 += 1L;
    }
    return (((double) num) / ((double) num2));
}

Fig: Average extension method working details.
From the above diagram we can see that the CLR will pass the list numbers as input to the Average method. This method will process the original list by iterating through it and calculate the average of items stored into the numbers list and return the average of the items as result.
The second version of the Average extension method will do the following steps,
Step 1: The CLR will pass the original list and the instance of the MulticastDelegate type created using the <Main>b_1 method (which is generated in the compile time by the compiler using anonymous method (x=>x*2) ) as input to the Average extension method.
Step 2: The CLR will call the Select method (public static IEnumerable<TResult> Select(this IEnumerable<TSource> source, Func selector) ), it will instantiate WhereSelectListIterator iterator from this method and send back to the Select method.
Step 3: The CLR will then call Average method which it will accept the iterator instance for example, WhereSelectListIterator created in Step 1 as input. This iterator will contain the original list and the instance of the MulticastDelegate as the Selector.
Step 4: In the Average method ForEach statement will iterate through the list
foreach (int num3 in source)
{
      num += num3;
      num2 += 1L;
}
and perform the average calculation. Following image shows,

Fig: Average extension method working details.
From the above diagram we can see that the CLR will pass the list numbers as input to the Average extension method (Average(this IEnumerable source, Func selector) ) along with the instance of MulticaseDelegate class instantiated from anonymous method (x=>x*2) code. The CLR will pass this to the Select method from where the appropiate iterator will be instantitated and return to the Average method. In this case it will be WhereSelectListIterator iterator will be passed to the Average method to process the original list. The WhereSelectListIterator iterator will hold the original list and the selector inside. From the average method CLR will iterate through the list and calculate the average based on the on the filtering criteria provided in the Selector.

Concat

This extension method concatenates two sequences. This method is implemented by using deferred execution (please read here for more about the deferred execution). The immediate return value is an instance one of the relevant iterator type that stores all the information that is required to perform the action. The query represented by this method is not executed until the object is enumerated either by calling its GetEnumerator method directly or by using foreach statement in C#.
The Concat<TSource>(IEnumerable<TSource>, IEnumerable<TSource>) method differs from the Union method because the Concat<TSource>(IEnumerable<TSource>, IEnumerable<TSource>) method returns all the original elements in the input sequences. The Union method returns only unique elements from the sequences. The method signature for this extension method is as below,
public static IEnumerable<TSource> Concat<TSource>(this IEnumerable<TSource> first, IEnumerable<TSource> second)
The following program will show the usage of the Concat method,
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<int> listOne = new List<int>() 
            { 
                1,2,3,4,5
            };

            IList<int> listTwo = new List<int>() 
            { 
                6,7,8,9,10
            };

            var result = listOne.Concat(listTwo).ToList();
            result.ForEach(x=> Console.WriteLine(x));


        }
    }
}
The above program will produce the following output,
1
2
3
4
5
6
7
8
9
10
The Concat extension works as below:

Fig: Concat extension method working details.
From the above diagram we can see that the CLR passed the listOne and listTwo as input to the Concat method and from the Concat method it will return ConcatIterator instance as output to the caller of this extension method. Though this will be executed using deferred execution pattern, the ToList() method will start processing using the logic implemented in the ConcatIterator class of listOne and listTwo to produce the final list.
When the CLR finds the Concat extension method it will execute following steps to perform the operation,
Step 1: The CLR will pass the original lists in this case listOne and listTwo to the Concat<TSource>(this IEnumerable<TSource> first, IEnumerable<TSource> second) method as input parameter.
Step 2: From the Concat method CLR will return an instance of the ConcatIterator<int> iterator which will hold the listOne and listTwo and return to the caller of the Concat method. The approximate code for the Concat method is as below,
public static IEnumerable<TSource> Concat<TSource>(this IEnumerable<TSource> first, IEnumerable<TSource> second)
{
    return ConcatIterator<TSource>(first, second);
}
Step 3: Due to the deferred execution this iterator will be executed by the ToList() method which will loop through the lists such as listOne and listTwo via the Enumerator object returned from the ConcatIterator instance and insert each of the item from listOne and listTwo to a new list and return as result.

Contains

The Contains extension method determines whether a sequence contains a specified element.
This method will work as below,
  • It determines whether a sequence contains a specified element by using the default equality comparer.
  • Determines whether a sequence contains a specified element by using a specified IEqualityComparer<T>.
The method signature for this extension method is as below,
public static bool Contains<TSource>(this IEnumerable<TSource> source, TSource value)
public static bool Contains<TSource>(this IEnumerable<TSource> source, TSource value, IEqualityComparer<TSource> comparer)
This method will search the list whether it has a particular value in it or not. To explain this method I wrote a small program:
using System;
using System.Collections;
using System.Collections.Generic;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<int> listOne = new List<int>() 
            { 
                1,2,3,4,5
            };

            var resultAsTrue = listOne.Contains(2);
            var resultAsFalse = listOne.Contains(200);
            Console.WriteLine("{0}\n{1}", resultAsTrue, resultAsFalse);
        }
    }
}
The above program will produce the following output,
True
False
So when the compiler finds the first version of the Contains method as in the above program, it will do the following steps to perform the operation,
  • The CLR will search a particular item into the list in the Contains method. This search will have two direction such as if the input is a null value then it will loop through the list to match item with the null and return true if one of the item from the list is null otherwise false. Other than null value CLR will compare the value (provided to match as input) with each of the item from the list, depending on match it will return a boolean answer.
The approximate code of the Contains method is as below,
public bool Contains(T item)
{
    if (item == null)
    {
        for (int j = 0; j < this._size; j++)
        {
            if (this._items[j] == null)
            {
                return true;
            }
        }
        return false;
    }

    EqualityComparer<T> comparer = EqualityComparer<T>.Default;
    for (int i = 0; i < this._size; i++)
    {
        if (comparer.Equals(this._items[i], item))
        {
            return true;
        }
    }
    return false;
}

Count

This count extension method returns the number of elements in a sequence.
The method signature for this extension method is as below,
public static int Count<TSource>(this IEnumerable<TSource> source)
public static int Count<TSource>(this IEnumerable<TSource> source, Func<TSource, bool> predicate)
The above two extension methods will do the followings,
  • First version returns the number of elements in a sequence.
  • Second version returns a number that represents how many elements in the specified sequence satisfy a condition.
The Count method will find out how many items in the list. For example in the following program I created a list of string objects. I use Count() method to find out how many items in the list and also how many items which is more than three characters.
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<string> listOne = new List<string>() 
            { 
                "One","Two","Three"
            };

            var result = listOne.Count();

            var fourOrMoreCharacters = listOne.Count(item => item.Length > 3);
            Console.WriteLine("{0}\n{1}", result,fourOrMoreCharacters);
        }
    }
}
The above program will produce the following output,
3
1
In this example I use two different version of Count method,
Step 1: When the CLR finds the first version of the Count method it will try to find out the Enumerator object of given list and iterate through items (using the iterator of the list) unless the MoveNext() method of the enumerator returns false.

Fig: Count extension method working details.
This method will return the number of iteration as the output of this program as the number of iteration will be the number of items in the list. The approximate code for the Count is as below,
public static int Count<TSource>(this IEnumerable<TSource> source)
{
    int num = 0;
    using (IEnumerator<TSource> enumerator = source.GetEnumerator())
    {
        while (enumerator.MoveNext())
        {num++;}
    }
    return num;
}
Step 2: The second version of the Count() method will accept the original list and a predicate to filter the count based on the condition. The predicate will be created in the compile time based on the anonymous method. The CLR will loop through the items of the list and execute the predicate over each of the item while looping through. If the predicate meet the condition over the item on iteration it will increase the item count. Finally it will return the item count as the total number of item which meets the condition. The approximate code for the Count method is as below,
public static int Count<TSource>(this IEnumerable<TSource> source, Func<TSource, bool> predicate)
{
    foreach (TSource local in source)
    {
        if (predicate(local))
        {
            num++;
        }
    }
    return num;
}

Fig: Count extension method working details.
From the above diagram we can see that the CLR passed the numbers list as input to the Count method along with the instance of the MulticastDelegate class created using <Main>b_1 which will created using the anonymous method (item=>item.Length > 3) code. In the count method CLR will iterate through each of the item and execute the delegate object against the item, depending on the return value of the delegate the number of count will increase and return the result as the total count of the list depends on the condition provided by (item=>item.Length > 3) .

DefaultIfEmpty

This extension method returns the elements of an IEnumerable<T>, or a default valued singleton collection if the sequence is empty. 
The signature for this extension method is as below:
public static IEnumerable<TSource> DefaultIfEmpty<TSource>(this IEnumerable<TSource> source)
public static IEnumerable<TSource> DefaultIfEmpty<TSource>(this IEnumerable<TSource> source, TSource defaultValue)
The above two extension methods will do the followings,
  • The first version returns the elements of the specified sequence or the type parameter's default value in a singleton collection if the sequence is empty.
  • The second version returns the elements of the specified sequence or the specified value in a singleton collection if the sequence is empty.
This method can be used on a list which does not have items in it and if we call the extension method over this list it will return default value of the item. Let’s see the following program which uses DefaultIfEmpty method:
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {

            IList<Person> persons = new List<Person>();
            IList<int> numbers = new List<int>();
            IList<string> names = new List<string>();

            var defaultPersons = persons.DefaultIfEmpty();

            var defaultNumbers = numbers.DefaultIfEmpty().ToList();

            var defaultNames = names.DefaultIfEmpty();
        }
    }

    class Person
    {
        public string Name
        {
            get;
            set;
        }

        public string Address
        {
            get;
            set;
        }

        public int Age
        {
            get;
            set;
        }
    }
}
In the above program I declared three lists of person objects, numbers and names of type Person, int and string accordingly. These three lists do not have any item and Count Property of this list will return 0. When I call the DefaultIfEmpty extension method over any of this list then the CLR will do the following steps to process it,
  • The CLR will copy the list to this DefaultIfEmpty method, from this method CLR will return the instance of the DefaultIfEmptyIterator<TSource> iterator which will hold the defaultvalue and source value. The defaultvalue property will contain the default value of the type of list and source will be the original list.
  • The CLR will pass the DefaultIfEmptyItereator to the ToList() method which will call the the List class passing the object of the DefaultIfEmptyItereator as input. In this class CLR will iterate through original list and process the result.

Fig: DefaultIfEmpty extension method working details.
The approximate code for the DefaultIfEmptyIterator is as below,
private static IEnumerable<TSource> DefaultIfEmptyIterator<TSource>(IEnumerable<TSource> source, TSource defaultValue)
{
    using (IEnumerator<TSource> iteratorVariable0 = source.GetEnumerator())
    {
        if (iteratorVariable0.MoveNext())
            do
            {
                yield return iteratorVariable0.Current;
            }
            while (iteratorVariable0.MoveNext());
        else
            yield return defaultValue;
    }
}

Distinct

This extension method returns distinct elements from a sequence.
The method signature of this extension method is as below,
public static IEnumerable<TSource> Distinct<TSource>(this IEnumerable<TSource> source)
public static IEnumerable<TSource> Distinct<TSource>(this IEnumerable<TSource> source, IEqualityComparer<TSource> comparer)
The above two extension methods will do the followings,
  • The first version returns distinct elements from a sequence by using the default equality comparer to compare values.
  • The second version returns distinct elements from a sequence by using a specified IEqualityComparer<T> to compare values.
The Distinct extension method will return the identical items from the list i.e. if we have a list which contains duplicate items using this method it will filtered the duplicated items and return a new list which will only contains the each of the item only once in the list. Let’s see the following program in where I use Distinct method on a list which contains a set of {1,1,1,2,2,2,3,3,3}.
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<int> numbers = new List<int>()
            {
                1,1,1,2,2,2,3,3,3
            };

            var distinctedNumbers = numbers.Distinct().ToList();
            distinctedNumbers.ForEach(x=>Console.WriteLine(x));
        }
    }
}
This program will produce following output,
1
2
3
When the above program will run it will produce {1, 2, 3} as output. Following diagram shows that how does distinct method works,

Fig: Distinct extension method working details.
To execute the Distinct method CLR will do the followings,
Step 1: The CLR will copy the original list to the Distinct method as input which will call the Distinct<TSource>(this IEnumerable<TSource> source, IEqualityComparer<TSource> comparer) method internally it will return an instance of the DistinctIterator<TSource>( IEnumerable<TSource> source, IEqualityComparer<TSource> comparer) class but this iterator will not execute due to the deferred execution (to execute the DistinctIterator iterator we need to call the ToList() method over the list or need to do the ForEach).
Step 2: From the ToList() method CLR will call the List class by passing the DistinctIterator created in Step 1 as input to it. The List class iterate through the instance of the DistinctIterator. The iteration logic implemented in the DistinctIterator will create a new instance of the Set<TSource> and iterates through the original list and adds the iterated item in the Set<TSource> instance it created earlier. Internally the Set<TSource> class will use Add and Find method to add the item from the given sequence into the internal slots array only when there is no duplicate item in the array slot. This will continue until CLR reaches the end of the list and will get a list with distinct items.
So the Distinct method will work as below over a list,
private static IEnumerable<TSource> DistinctIterator<TSource>(
    IEnumerable<TSource> source, IEqualityComparer<TSource> comparer)
{
    Set<TSource> iteratorVariable0 = new Set<TSource>(comparer);
    foreach (TSource iteratorVariable1 in source)
    {
        if (iteratorVariable0.Add(iteratorVariable1))
        {
            yield return iteratorVariable1;
        }
    }
}

ElementAt

This extension method returns the element at a specified index in a sequence.
The method signature for this extension method is as below,
public static TSource ElementAt<TSource>(this IEnumerable<TSource> source, int index)
public static TSource ElementAtOrDefault<TSource>(this IEnumerable<TSource> source, int index)
Following shows an example of ElementAt extension method of the IEnumerable<TSource> interface.
using System;
using System.Collections.Generic;
using System.Linq;
 
namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<string> numbers = new List<string>()
            {
                "One","Two","Three"
            };
 
            var elementAt = numbers.ElementAt(1);
 
            Console.WriteLine(elementAt);
        }
    }
}
This program is creating a numbers list which is storing One, Two and Three. From this numbers list I am trying to access the element which is stored in the position (array position) 1 and stored into the elementAt variable to display on the console. This program will produce the following output,
Two
To execute the ElementAt method the CLR will do the following things,
Step 1: The CLR will call the get_Item method from the System.Collections.Generic.List`1<T> class while executing the ElementAt<TSource>(this IEnumerable<TSource> source, int index) extension method. The following code has been extracted from the ElementAt method of the System.Linq.Enumerable class of the mscorlib.dll assembly using the ILDasm.exe program:
.method public hidebysig static !!TSource ElementAt<TSource>(
 class [mscorlib]System.Collections.Generic.IEnumerable`1<!!TSource> source,
       int32 index) cil managed
{
  IL_0018: ldloc.0
  IL_0019: ldarg.1
  IL_001a: callvirt   instance !0 class 
     [mscorlib]System.Collections.Generic.IList`1<!!TSource>::get_Item(int32)
  IL_001f: ret
} // end of method Enumerable::ElementAt
From the above code we can see that the CLR will call the get_Item(int32) method of the System.Collections.Generic.List`1<T> class with the index provided from the caller of the ElementAt method as input parameter in the label IL_001a.
Step 2: get_Item(int32) method of the System.Collections.Generic.List`1<T> class will load the _items array of this class (label IL_000f in the following IL code) and it will then load the argument (label IL_0014 in the following IL code) to get the index which will later use to access item from the _items array based on the index. If we see the IL code of the get_Item(int32) method from the System.Collections.Generic.List`1<T> class from the mscorlib.dll using ILDasm:
.method public hidebysig newslot specialname virtual final 
        instance !T  get_Item(int32 index) cil managed
{
  IL_000e:  ldarg.0
  IL_000f:  ldfld      !0[] class System.Collections.Generic.List`1<!T>::_items

  IL_0014:  ldarg.1
  IL_0015:  ldelem     !T

  IL_001a:  ret
} // end of method List`1::get_Item
From the above code ldfld IL instruction used in the IL_000f will load the _items field of the List<T> class and on IL_0014 label it will load the argument 1 which is the index will use to access the item from the _items array using the IL instruction ldelem used in the IL_0015.

Empty

Empty extension method returns an empty IEnumerable<T> that has the specified type argument.
The method signature for this extension is as below,
public static IEnumerable<TResult> Empty<TResult>()
Following example shows the usage of the Empty method,
using System;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            var emptyList = Enumerable.Empty<int>();

            Console.WriteLine(emptyList.Count());
        }
    }
}
In the above code I created an empty list of int type using the Empty() method. This program will produce the following output,
When the CLR will execute the Empty extension method it will do the following things to execute the operation.
Step 1: The CLR will call the get_Instance() method of the EmptyEnumerable`1<!!TResult> internal class from the System.Linq namespace of the System.Core.dll assembly while executing the Empty<TResult>() method. This class has an array field of given type (!!TResult) and a property Instance which will return the array field. The following IL code of the Empty method has been decompiled using the ILDasm.exe program from the System.Core.dll assembly.
.method public hidebysig static class 
 [mscorlib]System.Collections.Generic.IEnumerable`1<!!TResult> 
        Empty<TResult>() cil managed
{
  IL_0000:  call class [mscorlib]System.Collections.Generic.IEnumerable`1<!0> 
      class System.Linq.EmptyEnumerable`1<!!TResult>::get_Instance()
  IL_0005:  ret
} // end of method Enumerable::Empty
Step 2: The Instance property from the System.Linq.EmptyEnumerable`1<!!TResult> will call the get_Instance() method. The get_Instance() method will create an array with 0 items. The CLR will first push 0 onto the stack as int32 type using ldc.i4.0 IL instruction used in the label IL_0007 in the following code. Using the newarr IL instruction CLR will create a new array with the 0 item and will push on the stack. In the label IL_000d, CLR will use stsfld to replace the value of the field value i.e. instance field’s value using the value from the stack.
.method public hidebysig specialname static 
        class [mscorlib]System.Collections.Generic.IEnumerable`1<!TElement> 
        get_Instance() cil managed
{
  // Code size       24 (0x18)
  .maxstack  8
  IL_0000:  ldsfld     !0[] class System.Linq.EmptyEnumerable`1<!TElement>::'instance'
  IL_0005:  brtrue.s   IL_0012

  IL_0007:  ldc.i4.0
  IL_0008:  newarr     !TElement

  IL_000d:  stsfld     !0[] class System.Linq.EmptyEnumerable`1<!TElement>::'instance'
  IL_0012:  ldsfld     !0[] class System.Linq.EmptyEnumerable`1<!TElement>::'instance'

  IL_0017:  ret
} // end of method EmptyEnumerable`1::get_Instance

Except

The Except method can be used to remove a list of items from another. It produces the set difference of two sequences.
The method signature for this extension method is as below,
public static IEnumerable<TSource> Except<TSource>(this IEnumerable<TSource> first, IEnumerable<TSource> second)
public static IEnumerable<TSource> Except<TSource>(this IEnumerable<TSource> first, 
       IEnumerable<TSource> second, IEqualityComparer<TSource> comparer)
The above two extension methods will do the followings,
  • The first version produces the set difference of two sequences by using the default equality comparer to compare values.
  • the second version produces the set difference of two sequences by using the specified IEqualityComparer<T> to compare values.
The Except method can be used to remove a list of items from another. For example, if we have a list A with items {1,2,3,4,5,6,7} and B with {1,2,3} so the A except B will produce {4,5,6,7}. Following program used Except to show its usage,
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<int> firstNumbers = new List<int>()
            {
                1,2,3,4,5,6,7
            };
            IList<int> secondNumbers = new List<int>()
            {
                1,2,3
            };

            var result = firstNumbers.Except(secondNumbers).ToList();
            result.ForEach(x => Console.WriteLine(x));
        }
    }
}
This program will produce the following output,
4
5
6
7
When the above program will run it will produce the {4,5,6,7}. Following diagram shows that how the Except extension method works:

Fig: Except extension method working details.
The CLR will execute the Except method as following,
Step 1: The CLR will copy the original list to the Except method as input which will call the Except<TSource>(this IEnumerable<TSource> first, this IEnumerable<TSource> second, IEqualityComparer<TSource> comparer) method internally it will instantiate the ExceptIterator<TSource>( this IEnumerable<TSource> first, this IEnumerable<TSource> second, IEqualityComparer<TSource> comparer) iterator class. This iterator will not execute due to the deferred execution until the call the ToList() method over the list or use ForEach statement.
Step 2: When the CLR will execute the ToList() method it will call the List class by passing ExceptIterator instance created in Step 1 as input. The List class will call the ExceptIterator method while it iterates through the list. The ExceptIterator method creates a new instance of the Set<TSource> type and iterates through the second list and adds the iterated item in the Set instance it created earlier. Internally the method will use Add and Find method to add the item into the internal slots array only when there is no duplicate item in the slot. This will continue until compiler reaches the end of the second list. In the second loop CLR will iterate through the first list and try to add iterate item in the Set object it created in this step. If the item of second list does not exist in the set object then it will return that item and continue until it finishes the first list.
The approximate code of the ExceptIterator will be as below,
private static IEnumerable<TSource> ExceptIterator<TSource>(
    IEnumerable<TSource> first, 
    IEnumerable<TSource> second, 
    IEqualityComparer<TSource> comparer)
{
    Set<TSource> iteratorVariable0 = new Set<TSource>(comparer);
    foreach (TSource local in second)
    {
        iteratorVariable0.Add(local);
    }
    foreach (TSource iteratorVariable1 in first)
    {
        if (!iteratorVariable0.Add(iteratorVariable1))
        {
            continue;
        }
        yield return iteratorVariable1;
    }
}
So the Distinct method will work as below over a list,

First

It returns the first element of a sequence.
The method signature is be as below,
public static TSource First<TSource>(this IEnumerable<TSource> source)
public static TSource First<TSource>(this IEnumerable<TSource> source,Func<TSource, bool> predicate)
The above two First extension methods will do the following,
  • First version of this extension method will find out the first item from the sequence of items.
  • Second version of this extension method will find out the first item of list which meets the predicate condition.
I wrote a small program to explain the working steps for those two versions of the First extension methods of Enumerable class.
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<int> numbers = new List<int>()
            {
                1,2,3,4,5,6,7
            };

            var firstItem = numbers.First();
            var firstItemBasedOnConditions = numbers.First(item => item > 3);

            Console.WriteLine("{0}\n{1}",
                firstItem,
                firstItemBasedOnConditions
                );
        }
    }
}
This program will produce the following output:
1
4
When the CLR will execute the first version of the First extension method with following steps to perform the operation,
  • The CLR sends the original list to the First <TSource>(this IEnumerable<TSource> source) method as input parameter.
  • This method will return first item from the original list or iterate through the original list and return the first item from the iteration as a result.
The approximate code for this will be as below,
public static TSource First<TSource>(this IEnumerable<TSource> source)
{
    IList<TSource> list = source as IList<TSource>;
    if (list != null)
    {
        if (list.Count > 0)
        {
            return list[0];
        }
    }
    else
    {
        using (IEnumerator<TSource> enumerator = source.GetEnumerator())
        {
            if (enumerator.MoveNext())
            {
                return enumerator.Current;
            }
        }
    }
}
For the second version of the First extension method CLR will do following steps,
  • The compiler will construct a method <Main>b_1 using the anonymous (item => item > 3) . The CLR will pass this <Main>b_1 method to the MulticastDelegate class to construct an instance of it.
  • First method will loop through the list and match with each element in the sequence based on the predicate. This return on first match otherwise it will continue until find a match or not.
The approximate code for the,
public static TSource First<TSource>(
    this IEnumerable<TSource> source, 
    Func<TSource, bool> predicate)
{
    foreach (TSource local in source)
    {
        if (predicate(local))
        {
            return local;
        }
    }
}

FirstOrDefault

It returns the first element of a sequence, or a default value if no element is found.
The method signature for the FirstOrDefault extension is as below:
public static TSource FirstOrDefault<TSource>(this IEnumerable<TSource> source)
public static TSource FirstOrDefault<TSource>(this IEnumerable<TSource> source, Func<TSource, bool> predicate)
The above two extension method will do the followings,
  • It returns the first element of a sequence, or a default value if the sequence contains no elements.
  • It returns the first element of the sequence that satisfies a condition or a default value if no such element is found.
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<int> firstNumbers = new List<int>();

            IList<int> secondNumbers = new List<int>()
            {
                1,2,3,4,5,6,7
            };

            var firstItemOfFirstList = firstNumbers.FirstOrDefault();
            var firstItemIfFirstListBasedOnConditions =
                firstNumbers.FirstOrDefault(item => item > 3);

            var firstItemOfSecondList = secondNumbers.FirstOrDefault();
            var firstItemOfSecondListBasedOnConditions =
                secondNumbers.FirstOrDefault(item => item > 3);

            Console.WriteLine("{0}\n{1}\n{2}\n{3}",
                firstItemOfFirstList,
                firstItemIfFirstListBasedOnConditions,
                firstItemOfSecondList,
                firstItemOfSecondListBasedOnConditions
                );
        }
    }
}
This program will produce the following output,
0
0
1
4
Approximate code for the first version of the FirstOrDefault extension method:
public static TSource FirstOrDefault<TSource>(this IEnumerable<TSource> source)
{
    
    IList<TSource> list = source as IList<TSource>;
    if (list != null)
    {
        if (list.Count > 0)
        {
            return list[0];
        }
    }
    else
    {
        using (IEnumerator<TSource> enumerator = source.GetEnumerator())
        {
            if (enumerator.MoveNext())
            {
                return enumerator.Current;
            }
        }
    }
    return default(TSource);
}
Approximate for the second version of the FirstOrDefault extension method:
public static TSource FirstOrDefault<TSource>(
    this IEnumerable<TSource> source, 
    Func<TSource, bool> predicate)
{
    foreach (TSource local in source)
    {
        if (predicate(local))
        {
            return local;
        }
    }
    return default(TSource);
}

Union

The Union method will union (denoted as ?) of a collection of sets is the set of all distinct elements in the collection. For example, if we have two sets, A={1,2,3,4,5,6,7} and B={5,6,7,8,9} the Union of these sets will be A u B ={1,2,3,4,5,6,7,8,9}.
In .NET, the Union method will do the exactly as above diagram, it will join two list and create a new list.
public static IEnumerable<TSource> Union<TSource>(this IEnumerable<TSource> first, IEnumerable<TSource> second)
public static IEnumerable<TSource> Union<TSource>(this IEnumerable<TSource> first,
              IEnumerable<TSource> second, IEqualityComparer<TSource> comparer)
The following program shows the usage of the Union operation:
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<int> firstList = new List<int>() 
            { 
                1,2,3,4
            };

            IList<int> secondList = new List<int>() 
            { 
               7,9,3,4,5,6,7
            };

            var result = firstList.Union(secondList);
            result.ToList().ForEach(x => Console.WriteLine(x));
        }
    }
}
This program will produce the following output,
1
2
3
4
7
9
5
6
When the CLR will execute the Union method as below,
Step 1: The Union method will instantiate a UnionIterator<TSource> which will hold the firstList and the secondList and null for the IEqualityComparer as the above program does not provided any.
Step 2: Due to the deferred execution this UnionIterator<TSource> will be executed when the CLR will start executing the ToList() method. Inside the UnionIterator<TSource> a new instance of the Set<TSource> class will be instantiated which will be used to find out the distinct item from the both lists.
The approximate code for the UnitonIterator will be as below,
private static IEnumerable<TSource> UnionIterator<TSource>(
IEnumerable<TSource> first, 
IEnumerable<TSource> second, 
IEqualityComparer<TSource> comparer)
{
    Set<TSource> iteratorVariable0 = new Set<TSource>(comparer);

    foreach (TSource iteratorVariable1 in first)
    {
        if (iteratorVariable0.Add(iteratorVariable1))
        {
            yield return iteratorVariable1;
        }
    }
    foreach (TSource iteratorVariable2 in second)
    {
        if (!iteratorVariable0.Add(iteratorVariable2))
        {
            continue;
        }
        yield return iteratorVariable2;
    }
}

Intersect

It produces the set intersection of two sequences. The method signature for this extension method is as below:
public static IEnumerable<TSource> Intersect<TSource>(this IEnumerable<TSource> first, IEnumerable<TSource> second)
public static IEnumerable<TSource> Intersect<TSource>(this IEnumerable<TSource> first, 
              Enumerable<TSource> second,IEqualityComparer<TSource> comparer)
The above extension methods will do the followings,
  • It produces the set intersection of two sequences by using the default equality comparer to compare values.
  • It produces the set intersection of two sequences by using the specified IEqualityComparer<T> to compare values.
It produces the set intersection of two sequences. The intersect operation will produce those element which are common in the both list. For example, if we have a list A with items {1, 2, 3, 4, 5} and B with {4, 5} then the intersection of these two list A n B will produce {4, 5}

Fig: Intersect operation.
Let’s see the following program which is creating two list named listA with values 1, 2, 3, 4, 5, and listB with values 4, 5. I am doing an intersect operation between this two list using the Enumerable extension method Intersect.
using System;
using System.Collections.Generic;
using System.Linq;
 
namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<int> listA = new List<int>() { 1, 2, 3, 4, 5 };
            IList<int> listB = new List<int>() { 4, 5 };
 
            var intersectResult = listA.Intersect(listB);
 
            intersectResult.ToList().ForEach(x => Console.Write("{0}\t",x));
            Console.WriteLine();
        }
    }
}
This program will produce the following output:
4       5
To execute the Intersect extension method the CLR will do,
Step 1: The CLR will instantiate an instance of the IntersectIterator<TSource> and return to the caller. Due to the deferred execution this iterator will not execute until ToList() method is being called.
Step 2: From the IntersectIterator<TSource>, the CLR will create an instance of the Set<TSource> object which used to hold all the items from the second list. The CLR will then iterate through the first list and try to remove each of the items of the first list from the Set<TSource> object. If it can remove then it will return the item of the firstlist otherwise it will continue to iterate the first list until it can remove from the set. Following code shows the approximate code for the, IntersectIterator method,
private static IEnumerable<TSource> IntersectIterator<TSource>(
IEnumerable<TSource> first, 
IEnumerable<TSource> second, 
IEqualityComparer<TSource> comparer)
{
    Set<TSource> iteratorVariable0 = new Set<TSource>(comparer);

    foreach (TSource local in second)
    {
        iteratorVariable0.Add(local);
    }

    foreach (TSource iteratorVariable1 in first)
    {
        if (!iteratorVariable0.Remove(iteratorVariable1))
        {
            continue;
        }
        yield return iteratorVariable1;
    }
}

Last

It returns the last element of a sequence. 
The method signature for this extension method is as below,
public static TSource Last<TSource>(this IEnumerable<TSource> source)
public static TSource Last<TSource>(this IEnumerable<TSource> source, Func<TSource, bool> predicate)
The above two First extension methods will do the following
  • First version of this extension method will find out the first item from the sequence of items.
  • Second version of this extension method will find out the first item of list which meets the predicate condition.
I wrote a small program to explain the working steps for those two versions of Last extension methods of Enumerable class.
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<int> numbers = new List<int>()
            {
                1,2,3,4,5,6,7
            };

            var lastItem = numbers.Last();

            var lastItemBasedOnConditions = numbers.Last(item => item > 3);
        }
    }
}
When the CLR will execute the first version of the Last extension method as below,
  • The original list will be passed to the Last <TSource>(this IEnumerable<TSource> source) method as input parameter.
  • This method will loop through the list via the Enumerator object returns from the list and check whether the enumerator return a true value while calling the MoveNext() method of it and returns true otherwise false, i.e., the sequence does not have any element in it.
The approximate code for this will be as below,
public static TSource Last<TSource>(this IEnumerable<TSource> source)
{
    IList<TSource> list = source as IList<TSource>;
    if (list != null)
    {
        int count = list.Count;
        if (count > 0)
        {
            return list[count - 1];
        }
    }
    else
    {
        using (IEnumerator<TSource> enumerator = source.GetEnumerator())
        {
            if (enumerator.MoveNext())
            {
                TSource current;
                do
                {
                    current = enumerator.Current;
                }
                while (enumerator.MoveNext());
                return current;
            }
        }
    }
    throw Error.NoElements();
}
For the second version of the Any extension method CLR will do following steps,
  • The compiler will construct a method <Main>b_1 using the anonymous method (item => item > 3) in the compile time. The CLR will pass this <Main>b_1 method to the MulticastDelegate class to construct an instance of it and pass this <Main>b_1 to the Last extension method.
  • The CLR will loop through the list and match with each element in the sequence based on condition provided in the predicate. This return on first match otherwise it will continue until find a match or not.
The approximate code for the,
public static TSource Last<TSource>(
    this IEnumerable<TSource> source, 
    Func<TSource, bool> predicate)
{
    TSource local = default(TSource);
    bool flag = false;
    foreach (TSource local2 in source)
    {
        if (predicate(local2))
        {
            local = local2;
            flag = true;
        }
    }
    return local;
}

LastOrDefault

It returns the last element of a sequence, or a default value if no element is found.
The method signature for this extension method is as below,
public static TSource LastOrDefault<TSource>(this IEnumerable<TSource> source)
public static TSource LastOrDefault<TSource>(this IEnumerable<TSource> source, Func<TSource, bool> predicate)
The above extension method will for the followings,
  • It returns the last element of a sequence, or a default value if the sequence contains no elements.
  • It returns the last element of a sequence that satisfies a condition or a default value if no such element is found.
I wrote an example of discuss the LastOrDefault extension method,
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<int> firstNumbers = new List<int>();

            IList<int> secondNumbers = new List<int>()
            {
                1,2,3,4,5,6,7
            };

            var lastItemOfFirstList = firstNumbers.LastOrDefault();
            var lastItemIfFirstListBasedOnConditions =
                firstNumbers.LastOrDefault(item => item > 3);

            var lastItemOfSecondList = secondNumbers.LastOrDefault();
            var lastItemOfSecondListBasedOnConditions =
                secondNumbers.LastOrDefault(item => item > 3);

            Console.WriteLine("{0}\n{1}\n{2}\n{3}",
                lastItemOfFirstList,
                lastItemIfFirstListBasedOnConditions,
                lastItemOfSecondList,
                lastItemOfSecondListBasedOnConditions
                );
        }
    }
}
This program will produce the following output:
0
0
7
7
The approximate code of the first version of the LastOfDefault extension method is as below,
public static TSource LastOrDefault<TSource>(this IEnumerable<TSource> source)
{
    IList<TSource> list = source as IList<TSource>;
    if (list != null)
    {
        int count = list.Count;
        if (count > 0)
        {
            return list[count - 1];
        }
    }
    else
    {
        using (IEnumerator<TSource> enumerator = source.GetEnumerator())
        {
            if (enumerator.MoveNext())
            {
                TSource current;
                do
                {
                    current = enumerator.Current;
                }
                while (enumerator.MoveNext());
                return current;
            }
        }
    }
    return default(TSource);
}
The approximate code of the the second version of the LastOfDefault extension method is as below,
public static TSource LastOrDefault<TSource>(this IEnumerable<TSource> source, 
              Func<TSource, bool> predicate)
{
    TSource local = default(TSource);
    foreach (TSource local2 in source)
    {
        if (predicate(local2))
        {
            local = local2;
        }
    }
    return local;
}

LongCount

It returns an Int64 that represents the number of elements in a sequence. 
The method signature for this extension method is as below,
public static long LongCount<TSource>(this IEnumerable<TSource> source)
public static long LongCount<TSource>(this IEnumerable<TSource> source, Func<TSource, bool> predicate)
The above extension method will do as below,
  • Returns an Int64 that represents the total number of elements in a sequence.
  • Returns an Int64 that represents how many elements in a sequence satisfy a condition.
Let’s do an example,
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<int> firstList = new List<int>() 
            { 
                1,2,3,4
            };

            Console.WriteLine(firstList.LongCount());
        }
    }
}
The program will produce following output,
4
The approximate code of the the first version of the LongCount extension method is as below,
public static long LongCount<TSource>(this IEnumerable<TSource> source)
{
    long num = 0L;
    using (IEnumerator<TSource> enumerator = source.GetEnumerator())
    {
        while (enumerator.MoveNext())
        {
            num += 1L;
        }
    }
    return num;
}
The approximate code of the the second version of the LongCount extension method is as below,
 
public static long LongCount<TSource>(this IEnumerable<TSource> source, Func<TSource, bool> predicate)
{
    long num = 0L;
    foreach (TSource local in source)
    {
        if (predicate(local))
        {
            num += 1L;
        }
    }
    return num;
}

Max

In .NET, five overloaded Max extension methods have been defined in the Enumerable class.
public static int Max(this IEnumerable<int> source)
public static decimal Max<TSource>(this IEnumerable<TSource> source, Func<TSource, decimal> selector)
An example of the Max extension method is as below:
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<int> numbers = new List<int>() 
            { 
                1,2,3,4,5,6,7,8,9,10
            };

            Console.WriteLine("Max of the numbers :{0}", numbers.Max());

            Console.WriteLine("Max of the original numbers x2 :{0}", numbers.Max(x => x * 2));
        }
    }
}
The above program will produce following output,
Max of the numbers :10
Max of the original numbers x2 :20
So when the CLR finds the first version of the Max method in the above program, it will do the following steps to perform the operation,
Step 1: The CLR will pass the original list as input to the Max method.

Fig: Max extension method working details.
Step 2: The Max method will loop through the list and perform the Max operation.
The second version of the Max extension method will do the following steps,
Step 1: The compiler will construct a method <Main>b_1 using the anonymous method (x => x * 2). The CLR will pass this <Main>b_1 method to the MulticastDelegate class to construct an instance of it and call the Select method of the list which will take original list and the instance of the MulticastDelegate class as input. It will then return the relevant iterator instance for example, for the above example it will be WhereSelectListIterator<tsource,tresult> for the list as output.
Step 2: It will then call Max method which will accept only the Iterator. This Iterator will contain the original list and the instance of the MulticastDelegate. In the Max method ForEach method will iterate through the list and perform the max calculation.
Following image shows:

Fig: Max extension method working details.

Min

This extension method will find out the minimum of the list. The signature of the extension methods Min are below,
public static int Min(this IEnumerable<int> source)
public static int Min<TSource>(this IEnumerable<TSource> source, Func<TSource, int> selector)
An example of the Min Extension method is as below,
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<int> numbers = new List<int>() 
            { 
                1,2,3,4,5,6,7,8,9,10
            };

            Console.WriteLine("Min of the numbers :{0}", numbers.Min());

            Console.WriteLine("Min of the original numbers x2 :{0}", numbers.Min(x => x * 2));
        }
    }
}
The program will produce the following output,
Min of the numbers :1
Min of the original numbers x2 :2
So when the CLR finds the first version of the Min extension method as in the above program, it will do the following steps to perform the operation,
  • The CLR will pass the original list as input to the Min extension method.
  • The Min method will loop through the list and perform the minimum calculation operation.

Fig: Min extension method working details.
The second version of the Min extension method will do the following steps,
Step 1: The CLR will call the Select method of the list which will take original list and the instance of the MulticastDelegate which will be instantiated using the <Main>b_1 method. The <Main>b_1 method will be created in the compile time based on the anonymous method (x=>x*2). It will return the appropriate iterator which will be the WhereSelectListIterator and pass as input to the internal Min method.
Step 2: Inside the Min method CLR will perform the minimum calculation operation and return the result.
Following image shows,

Fig: Min extension method working details.

OfType

This extension method filters the elements of an IEnumerable based on a specified type using the deferred execution. The immediate return value is an object of the iterator class which stores all the information that is required to perform the action.
The signature of this extension method is as below,
public static IEnumerable<TResult> OfType<TResult>(this IEnumerable source)
Example of OfType<TResult>:
using System;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<object> numbers = new List<object>() 
            { 
                "One",
                "Two",
                1,
                2,
                "Three",
                new Person
                { 
                     Name="A Person"
                }
            };

            var filteredNumbers = numbers.OfType<string>();

            filteredNumbers.ToList().ForEach(x => Console.Write("{0}\t", x));
            Console.WriteLine();
        }
    }

    public class Person
    {
        public string Name { get; set; }
    }
}
The above program will filter string values from the numbers list as I set string in OfType method. So the program will produce following output,
One     Two     Three
Step 1: The CLR will pass the sequence for example numbers in the above example to the OfType method as input. Inside the OfType method the CLR will instantiate the OfTypeIterator which will hold the original sequence inside it. The approximate code for the OfType method is as below,
public static IEnumerable<TResult> OfType<TResult>(this IEnumerable source)
{
    return OfTypeIterator<TResult>(source);
}
Step 2: The CLR will pass the instance of the OfTypeIterator<TResult> class to the ToList() method which will pass this iterator to the List class and process the operation based on the iteration logic implemented in the OfTypeIterator and produce codethe ranged sequence as output.
The approximate code for the RangeIteraor is as below,
private static IEnumerable<TResult> OfTypeIterator<TResult>(IEnumerable source)
{
    IEnumerator enumerator = source.GetEnumerator();
    while (enumerator.MoveNext())
    {
        object current = enumerator.Current;
        if (current is TResult)
        {
            yield return (TResult) current;
        }
    }
}

Range

It generates a sequence of integral numbers within a specified range, implemented by using deferred execution. The immediate return value is an instance of the relevant iterator instance that stores all the information that is required to perform the action. The method signature for this extension method is as below,
public static IEnumerable<int> Range(int start, int count)

This method will create a list of int item based on the start number to till the number of times defined in the count.
using System;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            Enumerable.Range(1, 10).ToList().ForEach(x => Console.Write("{0}\t", x));
        }
    }
}
The program will produce the following output,
1       2       3       4       5       6       7       8       9       10
The CLR will do the followings,
Step 1: The CLR will pass the start element and no of times or the length of the generated sequence to the Range method as input. Inside the Range method the CLR will return the RangeIterator<int> which will hold all the related information such as start element and length of the sequence inside it. The approximate code for the Range method is as below,
public static IEnumerable<int> Range(int start, int count)
{
    long num = (start + count) - 1L;
    if ((count < 0) || (num > 0x7fffffffL))
    {
        throw Error.ArgumentOutOfRange("count");
    }
    return RangeIterator(start, count);
}
RangeIterator<int> will not be executed (due to the deferred execution) until the CLR call the ToList() method.

Fig: Range extension method
Step 2: The CLR will pass this RangeIterator<int> to the ToList() method which will pass this iterator instance to the List class and process the operation based on the iteration logic implemented in the RangeIterator<int> class and produce the ranged sequence as output. The approximate code for the RangeIteraor<int> is as below,
private static IEnumerable<int> RangeIterator(int start, int count)
{
    int iteratorVariable0 = 0;
    while (true)
    {
        if (iteratorVariable0 >= count)
        {
            yield break;
        }
        yield return (start + iteratorVariable0);
        iteratorVariable0++;
    }
}

Repeat

It generates a sequence that contains one repeated value is implemented by using deferred execution. The immediate return value is an object of the relevant iterator type that stores all the information that is required to perform the action.
The method signature of this extension method is as below,
public static IEnumerable<TResult> Repeat<TResult>(TResult element, int count)
It will generate a sequence of a number defined by the TResult type of a number of times measured by count.
using System;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            Enumerable.Repeat(1, 5).ToList().ForEach(x=>Console.Write("{0}\t",x));
        }
    }
}
The Repeat method of the Enumerable class will generate a sequence of 1 at 5 times inside. It will produce the following output,
1       1       1       1       1       
Step 1: The CLR will pass the element to repeat and no of times to repeat number to the Repeat method as input. Inside the Repeat method it will construct the RepeatIterator<TResult> iterator which will hold all the related information to generate the sequence.

Fig: Repeat extension method.
Step 2: The CLR will pass this RepeatIterator<TResult> instance to the ToList() method which will pass this iterator to the List class and process the operation based on the iteration logic implemented in the RepeatIterator<TResult> and produce the repeated sequence as output.
The approximate code for the Repeat method is as below,
private static IEnumerable<TResult> RepeatIterator<TResult>(TResult element, int count)
{
    int iteratorVariable0 = 0;
    while (true)
    {
        if (iteratorVariable0 >= count)
        {
            yield break;
        }
        yield return element;
        iteratorVariable0++;
    }
}

Reverse

It inverts the order of the elements in a sequence is implemented by using deferred execution. The immediate return value is an object of the iterator type that stores all the information that is required to perform the action. 
Unlike OrderBy, this sorting method does not consider the actual values themselves in determining the order. Rather, it just returns the elements in the reverse order from which they are produced by the underlying source.
public static IEnumerable<TSource> Reverse<TSource>(this IEnumerable<TSource> source)
It will reverse the original list, following example shows the usage of the Reverse extension method,
using System;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<int> numbers = new List<int>() { 1, 2, 3, 4, 5 };
            var reverseNumbers = numbers.Reverse();

            var result = reverseNumbers.ToList();

            result.ForEach(x => Console.Write("{0}\t", x));
            Console.WriteLine();
        }
    }
}
This program will produce the following output,
5       4       3       2       1
While the CLR will execute the above program, to process the Reverse method it will do the following steps,
Step 1: The CLR will pass the original sequence in this case the numbers object as input to the Reverse method. Inside the Reverse method it will construct the ReverseIterator<TSource> iterator which will hold all the information related to the original sequence.

Fig: Reverse extension method.
Step 2: The CLR will pass the ReverseIterator<TSource> instance to the ToList() method which will pass this iterator to the List class and process the operation based on the iteration logic implemented in the ReverseIterator<TSource> and produce the reversed sequence as output.
Approximate code for the ReverseIterator<TSource>:
private static IEnumerable<TSource> ReverseIterator<TSource>(
IEnumerable<TSource> source)
{
    Buffer<TSource> iteratorVariable0 = new Buffer<TSource>(source);
    int index = iteratorVariable0.count - 1;

    while (true)
    {
        if (index < 0)
        {
            yield break;
        }
        yield return iteratorVariable0.items[index];
        index--;
    }
}

Single

This extension method returns a single, specific element of a sequence.
The method signature for the extension method is as below,
public static TSource Single<TSource>(this IEnumerable<TSource> source)
public static TSource Single<TSource>(this IEnumerable<TSource> source, Func<TSource, bool> predicate)
public static TSource SingleOrDefault<TSource>(this IEnumerable<TSource> source)
public static TSource SingleOrDefault<TSource>(this IEnumerable<TSource> source,Func<TSource, bool> predicate)
The above extension method will do the followings,
  • It returns the only element of a sequence, and throws an exception if there is not exactly one element in the sequence.
  • It returns the only element of a sequence that satisfies a specified condition, and throws an exception if more than one such element exists.
I wrote a small program to test the Single extension method. In this program I will use the Single method over the IList<string> object numbers which contains only one item One. Following example will return One as output because this is the exactly one item in the list and the Single method works only those List object which contains exactly 1 item inside,
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
 
namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<string> numbers = new List<string>
            {
                "One"
            };
            var result = numbers.Single();
            Console.WriteLine("{0}", result);
        }
    }
}
The above program will produce following output,
One
If I modify the above code and add one more item in the numbers list and execute the program then we will get following error message,
Unhandled Exception: System.InvalidOperationException: Sequence contains more th
an one element
   at System.Linq.Enumerable.Single[TSource](IEnumerable`1 source)
   at Chapter_5.Program.Main(String[] args) in J:\Book\How Does it Work in C#\Bo
ok-Projects\HDIWIC\Chapter-5\Program.cs:line 16
Let’s now find out how does it works behind the scence,
Step 1: The CLR will make a new List<string> object using a copy of the original list and check whether the new list is null or not. If it is not null then it will check the number of items in the list. If the number of items in the list is 0 then the CLR will throw an exception otherwise it 1 then return the first and only item from the list. The approximate code will be as below,
public static TSource Single<TSource>(this IEnumerable<TSource> source)
{
    if (source == null)
    {
        throw Error.ArgumentNull("source");
    }
    IList<TSource> list = source as IList<TSource>;
    if (list != null)
    {
        switch (list.Count)
        {
            case 0:
                throw Error.NoElements();
                    
            case 1:
                return list[0];
        }
    }
    else
    {
        using (IEnumerator<TSource> enumerator = source.GetEnumerator())
        {
            if (!enumerator.MoveNext())
            {
                throw Error.NoElements();
            }
            TSource current = enumerator.Current;
            if (!enumerator.MoveNext())
            {
                return current;
            }
        }
    }
    throw Error.MoreThanOneElement();
}
Let’s try the Single extension method with a predicate function. I wrote a small program as below,
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<string> numbers = new List<string>
            {
                "One","Four"
            };
            var result = numbers.Single(x => x.Length > 3);
            Console.WriteLine("{0}", result);
        }
    }
}
This program will produce the following output,
Four
If I change the numbers list by adding one more item whose length is more than three character the program will fail by throwing following exception,
Unhandled Exception: System.InvalidOperationException: Sequence contains more th
an one matching element
   at System.Linq.Enumerable.Single[TSource](IEnumerable`1 source, Func`2 predic
ate)
   at Chapter_5.Program.Main(String[] args) in J:\Book\How Does it Work in C#\Bo
ok-Projects\HDIWIC\Chapter-5\Program.cs:line 16
I wrote an example of the SingleOrDefault extension method as below,
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<string> listStringWithoutItem = new List<string>();
            IList<string> listStringWithItem = new List<string>() { "One" };
            IList<int> listInt = new List<int>();
            IList<char> listChar = new List<char>();
            IList<long> listLong = new List<long>();
            IList<double> listDouble = new List<double>();

            var resultStringWithoutItem = listStringWithoutItem.SingleOrDefault();
            var resultStringWithItem = listStringWithItem.SingleOrDefault();
            var resultInt = listInt.SingleOrDefault();
            var resultChar = listChar.SingleOrDefault();
            var resultLong = listLong.SingleOrDefault();
            var resultDouble = listDouble.SingleOrDefault();

            Console.WriteLine("string : {0}", resultStringWithoutItem);
            Console.WriteLine("string : {0}", resultStringWithItem);
            Console.WriteLine("int : {0}", resultInt);
            Console.WriteLine("char : {0}", resultChar);
            Console.WriteLine("long : {0}", resultLong);
            Console.WriteLine("double : {0}", resultDouble);
        }
    }
}
The above will produce following output:
string :
string : One
int : 0
char :
long : 0
double : 0
The CLR will execute the SingleOrDefault extension with following steps,
Step 1: The CLR will check whether the list is null or not. If not then make a copy of the original into a temporary list. It will check the number of items in the list if it is 0 then the CLR will return the default value of the provided type for example, string for the listStringWithoutItem.SingleOrDefault<string>() or inferred type from the list for example, listStringWithoutItem is a type of IList<string> so the inferred type will be string .
The approximate code for the SingleOrDefault extension method is as below,
public static TSource SingleOrDefault<TSource>(this IEnumerable<TSource> source)
{
    IList<TSource> list = source as IList<TSource>;
    if (list != null)
    {
        switch (list.Count)
        {
            case 0:
                return default(TSource);
                    
            case 1:
                return list[0];
        }
    }
    else
    {
        using (IEnumerator<TSource> enumerator = source.GetEnumerator())
        {
            if (!enumerator.MoveNext())
            {
                return default(TSource);
            }
            TSource current = enumerator.Current;
            if (!enumerator.MoveNext())
            {
                return current;
            }
        }
    }
    throw Error.MoreThanOneElement();
}

Skip

It bypasses a specified number of elements in a sequence and then returns the remaining elements is implemented by using deferred execution. The immediate return value is an object of the relevant type that stores all the information that is required to perform the action. 
Skip method will iterate through the list and skip the specified number of items from the beginning of the list. The specified number will accept as parameter of the method.
public static IEnumerable<TSource> Skip<TSource>(this IEnumerable<TSource> source, int count)
The following program will create list of string type which will hold One, Two, Three, Four and Five as items of this list, On the list I applied the skip operation by providing 2 as the number of items to skip,
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<string> numbers = new List<string>() 
            { 
                "One","Two","Three", "Four","Five"
            };

            var result = numbers.Skip(2);
            result.ToList().ForEach(number => Console.WriteLine(number));
        }
    }
}
The program will produce following output,
Three
Four
Five
So the CLR will find the above code specially numbers.Skip(1) it will,
Step 1: The CLR will go to the Skip method of Enumerable class from the System.Linq namespace. This method will return the instance of the SkipIterator<TSource> which will hold the original list and the count which will define how many item to skip.
Step 2: As because of the deferred execution pattern, this SkipIterator<TSource> will execute while for iterate it via the ToList() method. So inside the SkipIterator method it will run a loop until the number of item to skip becomes 0. During this iteration it will move the current position of the inner Enumerator object. While the number of item becomes 0 then it will loop through the list again to return the remaining item from the list.
The approximate code of the SkipIterator is as below,
private static IEnumerable<TSource> SkipIterator<TSource>(
        IEnumerable<TSource> source, int count)
{
    using (IEnumerator<TSource> iteratorVariable0 = source.GetEnumerator())
    {
        while ((count > 0) && iteratorVariable0.MoveNext())
        {
            count--;
        }

        if (count <= 0)
        {
            while (iteratorVariable0.MoveNext())
            {
                yield return iteratorVariable0.Current;
            }
        }
    }
}

SkipWhile

This extension method bypasses elements in a sequence as long as a specified condition is true and then returns the remaining elements.
The method signature of this extension method is as below,
public static IEnumerable<TSource> SkipWhile<TSource>(this IEnumerable<TSource> source, Func<TSource, bool> predicate)
public static IEnumerable<TSource> SkipWhile<TSource>(this IEnumerable<TSource> source, Func<TSource, int, bool> predicate)
Let’s see an example of the SKipWhile extension method which will help to understand of this extension method,
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<string> numbers = new List<string>() 
            { 
                "One","Two","Three", "Four","Five"
            };

            var result = numbers.SkipWhile(number => number.Length == 3);
            result.ToList().ForEach(number => Console.WriteLine(number));
        }
    }
}
The above program will produce the following output,
Three
Four
Five
The output shows the result list excluded those items whose Length is equal to 3. So while the CLR find the SkipWhile method it will do the followings,
Step 1: The compiler will construct a method <Main>b_1 using the anonymous method (number => number.Length == 3) in the compile time. The CLR will pass this <Main>b_1 method to the MulticastDelegate class to instantiate an instance of it. So the CLR will pass the original list and predicate in this <Main>b_1 as input to the SkipWhile method and it will return SkipWhileIterator which will hold the original list and <Main>b_1 as predicate.
Step 2: Inside SkipWhileIterator, CLR will loop through the original list one by one and execute the predicate over the item. If the predicate return false then it will return that item as a result item of the SkipWhile method or otherwise if it return true then it will keep continue through the list until it finishes.
The approximate code for the SkipWhileIterator will be as below,
private static IEnumerable<TSource> SkipWhileIterator<TSource>(
    IEnumerable<TSource> source, Func<TSource, bool> predicate)
{
    bool iteratorVariable0 = false;
    foreach (TSource iteratorVariable1 in source)
    {
        if (!iteratorVariable0 && !predicate(iteratorVariable1))
        {
            iteratorVariable0 = true;
        }
        if (iteratorVariable0)
        {
            yield return iteratorVariable1;
        }
    }
}

Sum

To sum all the items inside a list we can use this Sum extension method. The signature of those methods is below,
public static int Sum(this IEnumerable<int> source)
public static int Sum<TSource>(this IEnumerable<TSource> source, Func<TSource, int> selector)
An example of the Min Extension method is as below,
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<int> numbers = new List<int>() 
            { 
                1,2,3,4,5,6,7,8,9,10
            };

            Console.WriteLine("Sum of the numbers :{0}", numbers.Sum());

            Console.WriteLine("Sum of the original numbers x2 :{0}", 
                numbers.Sum(x => x * 2));
        }
    }
}
The program will produce the following output,
Sum of the numbers :55
Sum of the original numbers x2 :110
To execute the first version of the Sum extension method used in the above program, CLR will do the following steps to perform the operation,
Step 1: The CLR will pass the original list as input to the Sum extension method.
Step 2: Inside the Sum method it will loop through the list and perform the summation of each of the item and produced the result and return as output of the Sum.

Fig: Sum Extension method
The approximate of the Sum method is as below,
public static int Sum(this IEnumerable<int> source)
{
    if (source == null)
    {
        throw Error.ArgumentNull("source");
    }
    int num = 0;
    foreach (int num2 in source)
    {
        num += num2;
    }
    return num;
}
To execute the second version of the Sum extension method CLR will execute following operations,
Step 1: The compiler will create a method <Main>b_1 using the anonymous method (x => x * 2) code.
Note: When I decompiled the produced executable from the above program using ILDasm.exe, there will be a method:
.method private hidebysig static int32 <Main>b__1(int32 x) cil managed
{
    .maxstack 2
    .locals init (
        [0] int32 CS$1$0000)
    L_0000: ldarg.0 
    L_0001: ldc.i4.2 
    L_0002: mul 
    L_0003: stloc.0 
    L_0004: br.s L_0006
    L_0006: ldloc.0 
    L_0007: ret 
}
The CLR will create an instance of MulticastDelegate instance using the <Main>b_1 method.
Step 2: The CLR will pass the original list and MulticastDelegate instance created in the Step 1 as input to the Sum method which will call the Select method with original list and the MulticastDelegate object as input. The CLR will instantiate the relevant iterator and return back to the Sum method. The CLR will then call the overloaded Sum() method.

Fig: Sum extension method working details.
Step 3: The CLR will iterate through the item from the original list based on the iterator and execute the given selector ie the delegate instance created in the Step 1 and sum all the modified item to complete the summation operation,

ThenBy

ThenBy extension method performs a subsequent ordering of the elements in a sequence in ascending order. This extension method is implemented by using deferred execution. The immediate return value is an object of the relevant type that stores all the information that is required to perform the action.
The signature of the ThenBy extension methods is as below,
public static IOrderedEnumerable<TSource> ThenBy<TSource, TKey>(this IOrderedEnumerable<TSource> source, Func<TSource, TKey> keySelector)
public static IOrderedEnumerable<TSource> ThenBy<TSource, TKey>(
       this IOrderedEnumerable<TSource> source, Func<TSource, TKey> keySelector, IComparer<TKey> comparer)
public static IOrderedEnumerable<TSource> ThenByDescending<TSource, TKey>(
       this IOrderedEnumerable<TSource> source, Func<TSource, TKey> keySelector)
public static IOrderedEnumerable<TSource> ThenByDescending<TSource, TKey>(
       this IOrderedEnumerable<TSource> source, Func<TSource, TKey> keySelector, IComparer<TKey> comparer)
I wrote this following program to explain the ThenyBy extension method,
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<Person> persons = new List<Person>() 
            { 
                new Person(){ Name="Person F", Address= "Address of F", Id= 111116},
                new Person(){ Name="Person G", Address= "Address of G", Id= 111117},
                new Person(){ Name="Person C", Address= "Address of C", Id= 111113},
                new Person(){ Name="Person B", Address= "Address of B", Id= 111112},
                new Person(){ Name="Person D", Address= "Address of D", Id= 111114},
                new Person(){ Name="Person A", Address= "Address of A", Id= 111111},
                new Person(){ Name="Person E", Address= "Address of E", Id= 111115}                
            };

            var result = persons.OrderBy(person => person.Id).ThenBy(person => person);

            foreach (Person person in result)
            {
                Console.WriteLine("{0,-15} {1,-20}{2,-20}",
                    person.Name,
                    person.Address,
                    person.Id);
            }
        }
    }


    public class Person
    {
        public string Name
        {
            get;
            set;
        }

        public string Address
        {
            get;
            set;
        }

        public double Id
        {
            get;
            set;
        }
    }
}
The above program will produce the following output,
Person A        Address of A        111111
Person B        Address of B        111112
Person C        Address of C        111113
Person D        Address of D        111114
Person E        Address of E        111115
Person F        Address of F        111116
Person G        Address of G        111117
It will work as,
Step 1: Code: Approximate code for the ThenBy method.
public static IOrderedEnumerable<TSource> ThenBy<TSource, TKey>(
this IOrderedEnumerable<TSource> source, 
Func<TSource, TKey> keySelector)
{
    return source.CreateOrderedEnumerable<TKey>(keySelector, null, false);
}
Step 2:
IOrderedEnumerable<TElement> IOrderedEnumerable<TElement>.CreateOrderedEnumerable<TKey>(
        Func<TElement, TKey> keySelector, IComparer<TKey> comparer, bool descending)
{
    return new OrderedEnumerable<TElement, TKey>(this.source, keySelector, 
           comparer, descending) { parent = (OrderedEnumerable<TElement>) this };
}
Step 2: The implementation of the Order
internal class OrderedEnumerable<TElement, TKey> : OrderedEnumerable<TElement>
{
    internal IComparer<TKey> comparer;
    internal bool descending;
    internal Func<TElement, TKey> keySelector;
    internal OrderedEnumerable<TElement> parent;
        
    internal OrderedEnumerable(IEnumerable<TElement> source, 
             Func<TElement, TKey> keySelector, 
             IComparer<TKey> comparer, 
             bool descending)
    {
        base.source = source;
        this.parent = null;
        this.keySelector = keySelector;
        this.comparer = (comparer != null) ? comparer : ((IComparer<TKey>) Comparer<TKey>.Default);
        this.descending = descending;
    }
        
    internal override EnumerableSorter<TElement> GetEnumerableSorter(
             EnumerableSorter<TElement> next)
    {
        EnumerableSorter<TElement> enumerableSorter = new 
          EnumerableSorter<TElement, TKey>(
           this.keySelector, 
           this.comparer, 
           this.descending, next);
        if (this.parent != null)
        {
            enumerableSorter = this.parent.GetEnumerableSorter(enumerableSorter);
        }
        return enumerableSorter;
    }
}

ToArray

It will create an array from the list. Following program will show the usage of the ToArray() method. The method signature is as below,
public static TSource[] ToArray<TSource>(this IEnumerable<TSource> source)
ToList<TSource> has similar behavior but returns a List<T> instead of an array.

Let’s see an example of the ToArray()
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<int> firstList = new List<int>() 
            { 
                1,2,3,4
            };

            var result = firstList.ToArray();
            result.ToList().ForEach(x => Console.WriteLine(x));
        }
    }
}
This program will produce the following output:
1
2
3
4
The CLR will execute the above as below,
Step 1: The CLR pass the original list as input to the ToArray<TSource>(this IEnumerable<TSource> source) method as input, inside the ToArray method it will create an instance of the Buffer<TSource> type by passing the original list object as input.
Step 2: The CLR will copy the each of the item from the original list to an internal array named items. The approximate code for the ToArray() method will be as below,
public static TSource[] ToArray<TSource>(this IEnumerable<TSource> source)
{
    Buffer<TSource> buffer = new Buffer<TSource>(source);

    return buffer.ToArray();
}
The internal of the Buffer<TSource> structure will be as below,
internal struct Buffer<TElement>
{
    internal TElement[] items;
    internal int count;
    internal Buffer(IEnumerable<TElement> source)
    {
        TElement[] array = null;
        int length = 0;
        ICollection<TElement> i.= source as ICollection<TElement>;
        if (i.!= null)
        {
            length = i..Count;
            if (length > 0)
            {
                array = new TElement[length];
                i..CopyTo(array, 0);
            }
        }
        else
        {
            foreach (TElement local in source)
            {
                if (array == null)
                {
                    array = new TElement[4];
                }
                else if (array.Length == length)
                {
                    TElement[] destinationArray = new TElement[length * 2];
                    Array.Copy(array, 0, destinationArray, 0, length);
                    array = destinationArray;
                }
                array[length] = local;
                length++;
            }
        }
        this.items = array;
        this.count = length;
    }
}
Step 3: And finally when the CLR calls the ToArray method, it will return:
internal TElement[] ToArray()
{
    if (this.count == 0)
    {
        return new TElement[0];
    }
    if (this.items.Length == this.count)
    {
        return this.items;
    }
    TElement[] destinationArray = new TElement[this.count];
    Array.Copy(this.items, 0, destinationArray, 0, this.count);
    return destinationArray;
}
A copy of the items array as output of the ToArray method.

ToDictionary

It creates a Dictionary<tkey,> from an IEnumerable<T>. If we want to create a dictionary object based on the data in a list this method will do everything by self but we need to specify a field from the list data as a key.
The signature of the ToDictionary extension is as below:
public static Dictionary<TKey, TSource> ToDictionary<TSource, TKey>(
       this IEnumerable<TSource> source, Func<TSource, TKey> keySelector)
public static Dictionary<TKey, TSource> ToDictionary<TSource, TKey>(
       this IEnumerable<TSource> source, 
       Func<TSource, TKey> keySelector, IEqualityComparer<TKey> comparer)
public static Dictionary<TKey, TElement> ToDictionary<TSource, TKey, TElement>(this IEnumerable<TSource> source, 
       Func<TSource, TKey> keySelector, Func<TSource, TElement> elementSelector)
public static Dictionary<TKey, TElement> ToDictionary<TSource, TKey, TElement>(this IEnumerable<TSource> source, 
       Func<TSource, TKey> keySelector, Func<TSource, TElement> elementSelector, IEqualityComparer<TKey> comparer)

Let’s see an example which will help to understand this ToDictionary method easily,
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<Person> persons = new List<Person>() 
            { 
                new Person(){ Name="Person A", Address= "Address of A", Id= 111111},
                new Person(){ Name="Person B", Address= "Address of B", Id= 111112},
                new Person(){ Name="Person C", Address= "Address of C", Id= 111113},
                new Person(){ Name="Person D", Address= "Address of D", Id= 111114},
            };

            var result = persons.ToDictionary(person => person.Id);
            
            foreach (KeyValuePair<double, Person> person in result)
            {
                Console.WriteLine("{0,-15} {1,-20}{2,-20}{3,-20}",
                    person.Key,
                    person.Value.Name,
                    person.Value.Address,
                    person.Value.Id);
            }
        }
    }


    public class Person
    {
        public string Name
        {
            get;
            set;
        }

        public string Address
        {
            get;
            set;
        }

        public double Id
        {
            get;
            set;
        }
    }
}
The above program will produce the following output,
111111          Person A            Address of A        111111
111112          Person B            Address of B        111112
111113          Person C            Address of C        111113
111114          Person D            Address of D        111114
I created a list of Person object and stored into a List object persons. Then I turned this persons list into a Dictionary using ToDictionary extension method. As we can see ToDictionary is taking an anonymous method as input. This anonymous method is actually a key selector which will select the key of the object from the list and set as key into the dictionary object. So from Person object, Id will be selected as key for the result dictionary and value will be person object itself, interesting enough the Id property will be used as Key for the Dictionary and also it will be stored into the person as it was initialized.
When the CLR do the following to execute the ToDictionary method,
Step 1: If we open the System.Linq.Enumerable namespace from the C:\Windows\Microsoft.NET\Framework\v4.0.30319\System.Core.dll assembly using ILDasm.exe program then we can see that the ToDictionary method interanlly call interanl ToDictionary method which has the following signature,
public static Dictionary<tkey,> ToDictionary<tsource,>( this IEnumerable<tsource> source, 
   Func<tsource,> keySelector, Func<tsource,> elementSelector, IEqualityComparer<tkey> comparer)
Before the CLR call the above internal ToDictionary method from the ToDictionary extension method, it will create an element selector function. In this case though I haven't provided any element selector the CLR will use the default element selector which is IdentityFunction<TSource>.Instance.
    Note:IdentityFunction<TSource>.Instance is an internal class which will be used as an element selector for the ToDictionary method. Following diagram shows this class from the System.Core.dll assembly,

    Fig: IdentityFunction
public static Dictionary<TKey, TSource> ToDictionary<TSource, TKey>(
    this IEnumerable<TSource> source, 
    Func<TSource, TKey> keySelector)
{
    return source.ToDictionary<TSource, TKey, TSource>(
        keySelector, IdentityFunction<TSource>.Instance, null);
}
Step 2: When the CLR goes to the above method, this method call overloaded ToDictionary as below,
public static Dictionary<TKey, TElement> ToDictionary<TSource, TKey, TElement>(
    this IEnumerable<TSource> source, 
    Func<TSource, TKey> keySelector, 
    Func<TSource, TElement> elementSelector, 
    IEqualityComparer<TKey> comparer)
{
    Dictionary<TKey, TElement> dictionary = new Dictionary<TKey, TElement>(comparer);
    foreach (TSource local in source)
    {
        dictionary.Add(keySelector(local), elementSelector(local));
    }
    return dictionary;
}
Which will instantiate an instance of the Dictionary<TKey, TElement> class. It will then iterate through the original list, each of the iterate value will pass to the KeySelector and ElementSelector function to extract the Key and Value from the iterate value.
As I provided (person => person.Id) as the KeySelector, the compiler will generate an anonymous method <Main>b_5 and pass to the KeySelector which will return the Id from the person object and compiler will provide the ElementSelector ( x=>x as in the IdentityFunction<telement> in where x=>x will converted as b__0) which will return the value itself, i.e., the person object with Name, Address and Id value inside.

ToList

It creates a List<T> from an IEnumerable<T>
The method signature for this extension method is as below,
public static List<TSource> ToList<TSource>(this IEnumerable<TSource> source)
To explain the working details of the ToList() extension method let’s see an example which is ToList() to produce the result,
I wrote a small program to show the usage of the ToList( this IEnumerable<TSource> collection) extension methods,
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<int> numbers = new List<int>() 
            { 
                1,2,3,4,5,6,7,8,9,10
            };

            var result = numbers.Where(x => x > 3).ToList();
            
            result.ForEach(x => Console.Write("{0}\t", x));
            Console.WriteLine();
        }
    }
}
The above program will produce following output as result,
4       5       6       7       8       9       10
So the CLR will execute the ToList() as below,
Step 1: The ToList() extension method will accept an IEnumerable object as input. It will pass this IEnumerable object as input to the List<TSource> type. The approximate code of that will be as below,
public static List<TSource> ToList<TSource>(this IEnumerable<TSource> source)
{
    return new List<TSource>(source);
}
Step 2: The List type will accept an IEnumerable<TSource> collection as input of the constructor. Inside the constructor the CLR will initialize the _items array with the type as TSource and define the initial size of the array with 4. It will then iterate through the enumerator of the input list object. The approximate code for the List constructor is be as below,
public List(IEnumerable<T> collection)
{
    ICollection<T> i. = collection as ICollection<T>;
    if (i. != null)
    {
        int count = i..Count;
        this._items = new T[count];
        i..CopyTo(this._items, 0);
        this._size = count;
    }
    else
    {
        this._size = 0;
        this._items = new T[4];
        using (IEnumerator<T> enumerator = collection.GetEnumerator())
        {
            while (enumerator.MoveNext())
            {
                this.Add(enumerator.Current);
            }
        }
    }
}

Fig: ToList() extension method working details.
Step 3: In the iteration phase each of the item the CLR will retrieve pass to the Add( TSource item) method to add into the _items array initialized (in the Step 2). The approximate code for the Add method is as below,
public void Add(T item)
{
    if (this._size == this._items.Length)
    {
        this.EnsureCapacity(this._size + 1);
    }
    this._items[this._size++] = item;
    this._version++;
}
In the Add method the most import code is the line this.EnsureCapacity(this._size + 1). The size of this _items array is dynamic and it will be ensured by the EnsureCapacity method.
Step 4: So after finishing the iteration the CLR will return the list object as the output of the ToList() method which will contain elements returned from the given IEnumerable<TSource> object inside the _items array.

Zip

It applies a specified function to the corresponding elements of two sequences, producing a sequence of the results. The method steps through the two input sequences, applying function resultSelector to corresponding elements of the two sequences. The method returns a sequence of the values that are returned by resultSelector. If the input sequences do not have the same number of elements, the method combines elements until it reaches the end of one of the sequences. For example, if one sequence has three elements and the other one has four, the result sequence has only three elements. The Zip extension method will combine two list items by item based on the provided combination logic. Based on the following method signature we can see it’s an extension of IEnumerable<TFirst> type and accept IEnumerable<TSecond> second, Func<TFirst, TSecond, TResult> resultSelector items as input.
The signature of this extension method is as below,
public static IEnumerable<TResult> Zip<TFirst, TSecond, TResult>(
    this IEnumerable<TFirst> first, IEnumerable<TSecond> second, 
    Func<TFirst, TSecond, TResult> resultSelector)

So the items of first and second list will be combined item by item together to produce a new list based on the combined logic provided into the resultSelector Func. So we can the Zip method will combine each of the item in the list as below,

Fig: An example of Zip extension method.
Based on the above diagram I wrote a small program which will combine the firstList which contains {1, 2, 3, 4} item with the secondList which contains {“One”,”Two”,”Three”,”Four”} with the combined logic, item from the first List + “:\t” + item from the secondList.
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;

namespace Chapter_5
{
    class Program
    {
        static void Main(string[] args)
        {
            IList<int> firstList = new List<int>() 
            { 
                1,2,3,4
            };

            IList<string> secondList = new List<string>() 
            { 
                "One","Two","Three","Four"
            };

            var result = firstList.Zip(secondList, (x, y) => x + ":\t" + y);
            
            result.ToList().ForEach(x => Console.WriteLine(x));
        }
    }
}
This program will produce following output as a result,
1:      One
2:      Two
3:      Three
4:      Four
So when the Compiler finds the Zip method it will,
Step 1: The compiler will construct a method <Main>b_2 using the anonymous method (x, y) => x + ":\t" + y. The CLR will pass this <Main>b_2 method to the MulticastDelegate class to instantiate an instance of it.
    Note: If we decompile the executable produced by the program and drop into the ILDasm.exe program we can see that the compiler generated following method block for the (x, y) => x + ":\t" + y code,
    .method private hidebysig static string  '<Main>b__2'(int32 x,
                                                          string y) cil managed
    {
      // Code size       22 (0x16)
      .maxstack  3
      .locals init ([0] string CS$1$0000)
      IL_0000:  ldarg.0
      IL_0001:  box        [mscorlib]System.Int32
      IL_0006:  ldstr      ":\t"
      IL_000b:  ldarg.1
      IL_000c:  call       string [mscorlib]System.String::Concat(object,
                                                                  object,
                                                                  object)
      IL_0011:  stloc.0
      IL_0012:  br.s       IL_0014
      IL_0014:  ldloc.0
      IL_0015:  ret
    } // end of method Program::'<Main>b__2' 
    
Step 2: The CLR will pass the instance of the MulticastDelegate created in the step1 to the Zip method which will return the ZipIterator instance after doing few basic null checks. The ZipIterator instance will hold the first and second list and resultSelector (instance of the MulticastDelegate created in step1) inside it.

Fig: The Zip method working details
Step 3: As this Zip extension method will execute using deferred execution pattern, whenever the CLR execute the ToList() method it will iterate through the ZipIterator enumerator. Inside the ZipIteraor enumerator CLR will iterate through each of the List and get the Current item from the each list and it will pass that Current item as input to the resultSelector Func as the input. The resultSelector will then combine each of the provided items into one single item (for example, 1 from the firstList and One from the secondList will be combined as 1: One) and return. This will continue until the both list has finished. In this iteration process if one of the list has less item than the other then it will only return same amount of item from the both list. For example, if list A has {A1,B1,C1,D1} items and B has{A2,B2,C2} then the result will be based on combination logic (+) processed result {A1A2, B1B2,C1C2}. The D1 from the A list will be deducted.
The approximate code for the Zip extension is as below,
public static IEnumerable<TResult> Zip<TFirst, TSecond, TResult>(
    this IEnumerable<TFirst> first, 
    IEnumerable<TSecond> second, 
    Func<TFirst, TSecond, TResult> resultSelector)
{
    return ZipIterator<TFirst, TSecond, TResult>(first, second, resultSelector);
}
        
private static IEnumerable<TResult> ZipIterator<TFirst, TSecond, TResult>(
    IEnumerable<TFirst> first, 
    IEnumerable<TSecond> second, 
    Func<TFirst, TSecond, TResult> resultSelector)
{
    using (IEnumerator<TFirst> iteratorVariable0 = first.GetEnumerator())
    {
        using (IEnumerator<TSecond> iteratorVariable1 = second.GetEnumerator())
        {
            while (iteratorVariable0.MoveNext() && iteratorVariable1.MoveNext())
            {
                yield return resultSelector(
                    iteratorVariable0.Current, 
                    iteratorVariable1.Current);
            }
        }
    }
}