Understanding Expression Trees

Preface
C# 3.0 came up with many interesting features including lamba expressions, field and collection initializers, anonymous types, type inference and other. One of them is expression trees – mysterious topic tightly coupled with LINQ.

This article will describe in details what expression trees are. It will also show you how to construct and how to use them in C# language. It will end up with answering several important question about expression trees – what is so special about them? Why and when to use them? And what is the difference between expression trees and lamba expressions?

This article assumes that you have at least decent knowledge about lambda expressions, as well as about LINQ (LINQ to objects especially).

 

Expression trees definition
In general, expression trees are special kind of binary trees. Binary tree is a tree in which all nodes contain zero, one or two children. Why expression trees have been implemented as binary trees? Mainly because binary trees allows you to quickly find what you are looking for. The upper limit of steps necessary to find required information in binary tree equals to log2N, where N denotes the number of all nodes in a tree.

Let`s give the following example careful consideration:

Func<int, int, bool> f = (a, b) => a < b;

It is a simple declaration of lambda expression that takes two numbers as parameters and returns true whenever first number is less than the second one and false otherwise. Fairly simple. But we could also write the same logic in an expression tree. What is the difference? Before answering this question, let`s take a look on how to create them.

 

Constructing expression trees
To create expression tree that refers to the previous example we have to use the following syntax:

Expression<Func<int, int, bool>> f = (a, b) => a < b;

Pretty much the same. The only difference is use of Expression<T> class. This class is somewhat handy as it contains four interesting properties holding useful information about underlying expression tree:

1.  Body

2.  NodeType

3.  Parameters

4.  Type

Alternatively, you could also build the same expression tree in other way – step by step:

ParameterExpression par1 = Expression.Parameter(typeof(int), "p1");

ParameterExpression par2 = Expression.Parameter(typeof(int), "p2");

BinaryExpression expr = Expression.LessThan(par1, par2);

 

var f = Expression.Lambda<Func<int, int, bool>>(expr, new ParameterExpression[] { par1, par2 });

Using expression trees
So far I shown that constructing expression trees is more difficult and complex than constructing simple lambda expressions. So is the way they are used. To use an expression tree you must first compile it:

var func = f.Compile();

From now on you can use as any other function:

var result = func(2,5);

Pretty much overhead, isn`t it? Then why bother yourself about expression trees if the same goals may be achieved using lambda expressions in simpler and faster way?

 

Expression trees purpose
In the previous example I shown that the given expression tree must be compiled before it can be used. This is because expression tree is actually a data structure, not compiled code. Why? Because this code is expected to be used across wire, or – in other words – in other processes (running possibly on other computers). For example – a query LINQ to SQL constructed on my machine will be send to database server. The server will construct itself-specific expression, run it and return requested values. It is much easier for external data providers to construct appropriate query based on expression tree (which is data structure) than based on compiled piece of code.

This does not apply to LINQ to objects however. In this case your queries will be run in the same process they were called and there is no need to create special data structure to represent your query. This is why in LINQ to objects lambda expressions may be used. In all other cases you must rely on expression trees.

 

Summary
Expression trees are very interesting concept. At the beginning it might seem that they simply double up the functionality offered by lambda expressions. The difference is noticeable however when different kinds of LINQ than LINQ to objects are used. In such cases your queries will be send across wire and run in different process and possibly on different machine. Cool idea that makes such scenarios possible and is very easy and straightforward.

posted @ Monday, June 29, 2009 1:36 AM
Print

Comments on this entry:

# re: Understanding expression trees

Left by Bill Craun at 7/2/2009 7:17 PM
Gravatar
In paragraph 1, I believe you mean "type inference" and not "tpe interference".

# re: Understanding Expression Trees

Left by Martinez at 10/29/2009 11:42 AM
Gravatar
Yes indeed! Thank you for correction.

# re: Understanding Expression Trees

Left by thangchung at 4/24/2010 1:00 AM
Gravatar
I just wrote the article about Converting Expression Tree and referenced to your article. Thanks for your post, it's really clear when explained about Expression Tree is a Data Structure.
Regards

# re: Understanding Expression Trees

Left by Monisgnor at 8/24/2010 9:33 PM
Gravatar
Thanks, no I've finally understood what is expression trees!

# re: Understanding Expression Trees

Left by Prayag Potnis at 3/18/2011 12:35 AM
Gravatar
Very nice article indeed, it explains the concept in simple words and good example.

# re: Understanding Expression Trees

Left by Andrew Wrigley at 9/22/2011 5:15 AM
Gravatar
Many thanks.

# re: Understanding Expression Trees

Left by Tarik at 11/26/2011 4:54 AM
Gravatar
Thanks for this amazing article.

# re: Understanding Expression Trees

Left by burkskurk at 12/21/2011 8:00 AM
Gravatar
the best post i've read on this topic by far. thanks!

# re: Understanding Expression Trees

Left by James Wiseman at 3/23/2012 4:04 AM
Gravatar
Brilliant. Thanks for the explanation

# re: Understanding Expression Trees

Left by Bruce at 6/25/2012 6:30 PM
Gravatar
Clear and Good explanation.

# re: Understanding Expression Trees

Left by maz3tt at 10/8/2012 10:29 PM
Gravatar
finally i understood that why expression trees were born. thanks

# re: Understanding Expression Trees

Left by reza at 11/9/2012 2:52 PM
Gravatar
Thank you so much

# re: Understanding Expression Trees

Left by Nandha Kumar at 11/25/2013 12:20 AM
Gravatar
Nice preliminary explanation, thank you

Your comment:



(not displayed)

 
 
 
 
 

Live Comment Preview:

 
«July»
SunMonTueWedThuFriSat
293012345
6789101112
13141516171819
20212223242526
272829303112
3456789