Append and Prepend in IEnumerable object

/// <summary>Adds a single element to the end of an IEnumerable.</summary>
        /// <typeparam name=”T”>Type of enumerable to return.</typeparam>
        /// <returns>IEnumerable containing all the input elements, followed by the
        /// specified additional element.</returns>
        public static IEnumerable<T> Append<T>(this IEnumerable<T> source, T element)
        {
            if (source == null)
                throw new ArgumentNullException(“source”);
            return concatIterator(element, source, false);
        }

        /// <summary>Adds a single element to the start of an IEnumerable.</summary>
        /// <typeparam name=”T”>Type of enumerable to return.</typeparam>
        /// <returns>IEnumerable containing the specified additional element, followed by
        /// all the input elements.</returns>
        public static IEnumerable<T> Prepend<T>(this IEnumerable<T> tail, T head)
        {
            if (tail == null)
                throw new ArgumentNullException(“tail”);
            return concatIterator(head, tail, true);
        }

        private static IEnumerable<T> concatIterator<T>(T extraElement,
            IEnumerable<T> source, bool insertAtStart)
        {
            if (insertAtStart)
                yield return extraElement;
            foreach (var e in source)
                yield return e;
            if (!insertAtStart)
                yield return extraElement;
        }

Create List Heirarchy from flat collection of entities

namespace TUEMIS.Common
{
    public static class TreeExtensions
    {
private static IEnumerable<TreeNode<TEntity>> CreateHierarchy<TEntity, TProperty>(IEnumerable<TEntity> items, TEntity parentItem,
            Func<TEntity, TProperty> idProperty, Func<TEntity, TProperty> parentIdProperty, int level, Func<TEntity, TProperty> orderBy) where TEntity : class
        {
            items = items.OrderBy(orderBy);

            IEnumerable<TEntity> childs;
            if (parentItem == null)
                childs = items.Where(i => parentIdProperty(i).Equals(default(TProperty)));
            else
                childs = items.Where(i => parentIdProperty(i).Equals(idProperty(parentItem)));

            if (childs.Any())
            {
                level++;
                foreach (var item in childs)
                {
                    yield return new TreeNode<TEntity>
                    {
                        Entity = item,
                        Children = CreateHierarchy<TEntity, TProperty>(items, item, idProperty, parentIdProperty, level, orderBy).ToList(),
                        Level = level
                    };
                }
            }
        }

        /// <summary>
        /// LINQ IEnumerable AsHierachy() extension method
        /// </summary>
        /// <typeparam name=”TEntity”>Entity class</typeparam>
        /// <typeparam name=”TProperty”>Property of entity class</typeparam>
        /// <param name=”items”>Flat collection of entities</param>
        /// <param name=”idProperty”>Reference to Id/Key of entity</param>
        /// <param name=”parentIdProperty”>Reference to parent Id/Key</param>
        /// <returns>Hierarchical structure of entities</returns>
        public static IEnumerable<TreeNode<TEntity>> AsHierarchy<TEntity, TProperty>(this IEnumerable<TEntity> items, Func<TEntity, TProperty> idProperty, Func<TEntity, TProperty> parentIdProperty, Func<TEntity, TProperty> orderBy) where TEntity : class
        {
            return CreateHierarchy(items, default(TEntity), idProperty, parentIdProperty, 0, orderBy);
        }
}
}

    public class TreeNode<T>
    {
        public TreeNode()
        {
            Children = new List<TreeNode<T>>();
        }
        public T Entity { get; set; }
        public int Level { get; set; }
        public List<TreeNode<T>> Children { get; set; }
    }

USING MORELINQ TO SELECT DISTINCT BY PROPERTY NAME

LINQ provides two overridden functions to select distinct elements only, either by default equality comparer or user defined one. However, there are cases where elements are to be selected only on base of a single or some set or properties.
This can be achieved by user defined set of codes that takes property as argument to filter by.
Below is the code:

public static IEnumerable<TSource> DistinctBy<TSource, TKey>(this IEnumerable<TSource> source, Func<TSource, TKey> keySelector)
        {
            var seenKeys = new HashSet<TKey>();
            return source.Where(element => seenKeys.Add(keySelector(element)));
        }


The code below is used as method extension for IEnumerable DataSource. And using the defined key selector, the IEnumerable List if filtered by distinct based on the key selector.
e.g
var listSamples=new List<MyObject>();
var newdistinctList=listSamples.DistinctBy(o=>o.MyProperty);

However for selecting mutliple columns unique, following code can be used:
var newDistinctList2=listSamples.DistinctBy(o=> new {o.MyProperty1, o.MyProperty2});

OBJECT EQUALITY COMPARISON C#

Any two objects of same type has to be compared for equality. For this we have an internal function as Enumerable.SequenceEqual(). But this can compare equality of two objects provided only if the elements are in their respective order.
i. .e if A={1, 2, 3} and B={1, 2, 3} then they are equal and returns true but if B={3, 1, 2} then these two objects are not equal from above function.
But in this case where the order of the elements of the object can be ignored while comparing by our own method extension function, defined as below:

public static bool UnorderedEqual<T>(this ICollection<T> a, ICollection<T> b)
        {
            // 1
            // Require that the counts are equal
            if (a.Count != b.Count)
            {
                return false;
            }
            // 2
            // Initialize new Dictionary of the type
            Dictionary<T, int> d = new Dictionary<T, int>();
            // 3
            // Add each key’s frequency from collection A to the Dictionary
            foreach (T item in a)
            {
                int c;
                if (d.TryGetValue(item, out c))
                {
                    d[item] = c + 1;
                }
                else
                {
                    d.Add(item, 1);
                }
            }
            // 4
            // Add each key’s frequency from collection B to the Dictionary
            // Return early if we detect a mismatch
            foreach (T item in b)
            {
                int c;
                if (d.TryGetValue(item, out c))
                {
                    if (c == 0)
                    {
                        return false;
                    }
                    else
                    {
                        d[item] = c – 1;
                    }
                }
                else
                {
                    // Not in dictionary
                    return false;
                }
            }
            // 5
            // Verify that all frequencies are zero
            foreach (int v in d.Values)
            {
                if (v != 0)
                {
                    return false;
                }
            }
            // 6
            // We know the collections are equal
            return true;
        }

PIVOTING IN IENUMERABLE OBJECT C#

We can pivot IEnumerable source as we can perform pivoting in sql. This is similar to pivoting in SQL, however, the no of columns that has to be pivoted is static. Whereas, in SQL dynamic pivoting can be performed with PL-SQL. Here’s how we do it in c# IEnumerable object.

Extension:

using System;using System.Collections.Generic;
using System.Linq;
namespace Common.LinqExtensions
{
     public static class LinqExtenions
    {
        public static Dictionary<TFirstKey, Dictionary<TSecondKey, TValue>> Pivot<TSource, FirstKey, TSecondKey, TValue>(this IEnumerable<TSource> source, Func<TSource, TFirstKey> firstKeySelector, Func<TSource, TSecondKey> secondKeySelector, Func<IEnumerable<TSource>, TValue> aggregate)
{           
    var retVal = new Dictionary<TFirstKey, Dictionary<TSecondKey, TValue>>();            
    var l = source.ToLookup(firstKeySelector);           
    foreach (var item in l)
     {
        var dict = new Dictionary<TSecondKey, TValue>();               
        retVal.Add(item.Key, dict);               
        var subdict = item.ToLookup(secondKeySelector);               
        foreach (var subitem in subdict)
        {
            dict.Add(subitem.Key, aggregate(subitem));
         }
      }            
    return retVal;       
}    
}
}




Example:


class Program 
{     
    internal class Employee 
    {        
    public string Name { get; set; }        
    public string Department { get; set; }        
    public string Function { get; set; }        
    public decimal Salary { get; set; }    
    }     
    static void Main(string[] args) 
    {         
        var l = new List<Employee>()
     {
        new Employee() { Name = “Fons”, Department = “R&D”, Function = “Trainer”, Salary = 2000 },            
        new Employee() { Name = “Jim”, Department = “R&D”, Function = “Trainer”, Salary = 3000 },     
        new Employee() { Name = “Ellen”, Department = “Dev”, Function = “Developer”, Salary = 4000 },      
        new Employee() { Name = “Mike”, Department = “Dev”, Function = “Consultant”, Salary = 5000 },            
        new Employee() { Name = “Jack”, Department = “R&D”, Function = “Developer”, Salary = 6000 },       
        new Employee() { Name = “Demy”, Department = “Dev”, Function = “Consultant”, Salary = 2000 }};         
        var result1 = l.Pivot(emp => emp.Department, emp2 => emp2.Function, lst => lst.Sum(emp => emp.Salary));       
  
        foreach (var row in result1)
       {            
            Console.WriteLine(row.Key);            
            foreach (var column in row.Value) 
            {                
                Console.WriteLine(”  ” + column.Key + “\t” column.Value); 
            }        
        }      

   Console.WriteLine(“—-“);         

    var result2 = l.Pivot(emp => emp.Function, emp2 => emp2.Department, lst => lst.Count());         

    foreach (var row in result2) 
    {            
        Console.WriteLine(row.Key);            
        foreach (var column in row.Value) 
        {
            Console.WriteLine(”  ” + column.Key + “\t” + column.Value);  
           }        
    }         
Console.WriteLine(“—-“);
}}

Combinations of IEnumerable Source

SOURCE CODE

/// <summary>
///   Returns all combinations of a chosen amount of selected elements in the sequence.
/// </summary>
/// <typeparam name = “T”>The type of the elements of the input sequence.</typeparam>
/// <param name = “source”>The source for this extension method.</param>
/// <param name = “select”>The amount of elements to select for every combination.</param>
/// <param name = “repetition”>True when repetition of elements is allowed.</param>
/// <returns>All combinations of a chosen amount of selected elements in the sequence.</returns>
public static IEnumerable<IEnumerable<T>> Combinations<T>( this IEnumerable<T> source, int select, bool repetition = false )
{   
    Contract.Requires( source != null );   
    Contract.Requires( select >= 0 );    
    return select == 0       
        ? new[] { new T[0] }       
        : source.SelectMany( ( element, index ) =>            source
                .Skip( repetition ? index : index + 1 )
                .Combinations( select – 1, repetition )               
                .Select( c => new[] { element }.Concat( c ) ) );
}

EXAMPLE

int[] numbers = new[] { 0, 1 };
var result = numbers.Combinations( 2, true );
// result == {{0, 0}, {0, 1}, {1, 0}, {1, 1}}