Creating a LINQ Expression where parameter equals object

前端 未结 3 990
野性不改
野性不改 2021-02-07 00:18

Given a primitive value age I know how to create an expression like this:

//assuming: age is an int or some other primitive type
employee => empl         


        
3条回答
  •  说谎
    说谎 (楼主)
    2021-02-07 00:58

    Give the code below a run. I wanted to test your assumption that e => e.Location == location is compiling into something that can be constructed with Expression.Equal, Expression.Property, and Expression.Constant.

        class Program {
           static void Main(string[] args) {
              var location = new Location();
              Expression> expression = e => e.Location == location;
    
              var untypedBody = expression.Body;
    
              //The untyped body is a BinaryExpression
               Debug.Assert(
                  typeof(BinaryExpression).IsAssignableFrom(untypedBody.GetType()), 
                  "Not Expression.Equal");
    
               var body = (BinaryExpression)untypedBody;
               var untypedLeft = body.Left;
               var untypedRight = body.Right;
    
               //The untyped left expression is a MemberExpression
               Debug.Assert(
                  typeof(MemberExpression).IsAssignableFrom(untypedLeft.GetType()), 
                  "Not Expression.Property");
    
               ////The untyped right expression is a ConstantExpression
              //Debug.Assert(
              //   typeof(ConstantExpression).IsAssignableFrom(untypedRight.GetType()),                 
              //   "Not Expression.Constant");
    
              //The untyped right expression is a MemberExpression?
              Debug.Assert(
                   typeof(MemberExpression).IsAssignableFrom(untypedRight.GetType())));
        }
    }
    
    public class Employee
    {
        public Location Location { get; set; }
    }
    
    public class Location { }
    

    It seems like it isn't, and its because the right expression isn't a Constant. To see this, uncomment the commented out code.

    What I don't understand is why the right expression is a MemberExpression. Perhaps someone who knows the linq expression compiler can shed more light onto this then I can.

    Edit: This may have to do with closure in lambdas - a class is created behind the scenes which contains the closed over variables. The location might then be a member of that class. I'm not sure about this, but it's what I suspect.

    This post may shed additional light on the situation.

提交回复
热议问题