Generic Lambda Expression to sort collections of different types
Suppose you have many collections with different types that you want to sort, of course you can do it by OrderBy or OrderByDescending extension methods but you have to specify the order criteria every time you call these methods. If the order criteria is determined in runtime, then you have to build a separate function to each order criteria of each type. To clear what I want to tell you suppose you have two classes, Employee and Department.
OrderBy and OrderByDescending methods need Func<TSource,TKey> as selector to compare the collection items and order them. So the issue here is, How do you create a generic Func<TSource,TKey> to be passed to OrderBy or OrderByDescending methods? The answer is, by using Expression.Lambda method.
We will create a generic method with one string argument which will be the name of the property that we will order by and the return will be Lambda expression will be passed to OrderBy or OrderByDescending.
you can download the full source code here
public class Employee
{
public String Name { get; set; }
public Int32 Age { get; set; }
public DateTime HiringDate { get; set; }
}
public class Department
{
public String DepartmentName { get; set; }
public String Code { get; set; }
}
And you want to order the employee collection by one of its properties (Name,Age,or HiringDate) and order department collection by one of its properties.OrderBy and OrderByDescending methods need Func<TSource,TKey> as selector to compare the collection items and order them. So the issue here is, How do you create a generic Func<TSource,TKey> to be passed to OrderBy or OrderByDescending methods? The answer is, by using Expression.Lambda method.
We will create a generic method with one string argument which will be the name of the property that we will order by and the return will be Lambda expression will be passed to OrderBy or OrderByDescending.
public Func<T, Object> GetExpression<T>(String sortby)
{
var param = Expression.Parameter(typeof(T));
var sortExpression = Expression.Lambda<Func<T, Object>>(Expression.Convert(Expression.Property(param, sortby), typeof(Object)), param);
return sortExpression.Compile();
}
The GetExpression method do the following:
- Create ParameterExpression object by calling Expression.Parameter method which accepts the type of the collection we want to sort.
- Create the Lambda expression tree.
- Compile the lambda expression by calling Expression.Compile method and return a delegate that represent the lambda expression.
employees.OrderBy(GetExpression("Age"));
departments.OrderBy(GetExpression("Code"));
First line will order employees by according to their ages and the second line will order departments by its codes.
you can download the full source code here
Sorting expression for gridview
ReplyDeleteHI,
ReplyDeletevery good article... thanks
Excelent work. Thank you.
ReplyDelete