c# - 创建包含外部变量的 LambdaExpression

标签 c# linq entity-framework lambda entity-framework-5

我想创建类似这样的 lambda

user => user.Address == address

但不是编译一个,我想返回LambdaExpression

如果 lambda 像这样取常量

user => user.Age == 50

那我就可以用这个方法了

    public static LambdaExpression PropertyEqual(Type tEntityType, string propertyName, object value)
    {
        // entity => entity.PropName == const
        var itemParameter = Expression.Parameter(tEntityType, "entity");
        return Expression.Lambda
        (
            Expression.Equal
            (
                Expression.Property
                (
                    itemParameter,
                    propertyName
                ),
                Expression.Constant(value) // Tried to replace this with Expression.Parameter or Expression.Variable but no luck
            ),
            new[] { itemParameter }
        );
    }

如何使此方法接受来自 lambda 表达式外部范围的变量 address

var addressPropertyName = "Address";
var address = new Address() {...};
var q = Repo.GetQuery().Where(PropertyEqual(typeof(User), addressPropertyName, address))

编辑:澄清我的问题:How build the right Expression to generate the first lambda?

更新:这是不可能的,因为EF does not support non-scalar variable

我按照建议将 lambda 更改为 user => user.AddressId == addressId here .问题在于如何从已知的导航属性 Address 中获取 AddressId FK PropertyInfo

最佳答案

您不能在变量上动态生成闭包(您不能在其上下文之外延长变量的生命周期),因为这是编译器的一个技巧(它会重写您的代码来执行此操作)。

如果您不需要闭包但需要额外的参数,那么您可以向表达式添加额外的参数。

你可以

Expression<Func<string>> myExpr = () => address;

现在您的地址周围有一个表达式。现在您只需要组合这两个表达式。

您必须将方法更改为:

public static LambdaExpression PropertyEqual<T>(Type tEntityType, string propertyName, Expression<Func<T>> getValue)
{
   // entity => entity.PropName == const
   var itemParameter = Expression.Parameter(tEntityType, "entity");
   return Expression.Lambda
   (
       Expression.Equal
       (
           Expression.Property
           (
               itemParameter,
               propertyName
           ),
           Expression.Invoke(getValue) // You could directly use getValue.Body instead of Expression.Invoke(getValue)
       ),
       new[] { itemParameter }
   );
}

关于c# - 创建包含外部变量的 LambdaExpression,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/17991079/

相关文章:

c# - 使用反射构建 Dapper SQL Builder 查询参数

c# - 当属性不能为 null 时使用什么异常类型?

sql-server - Entity Framework Core 3.1.1 查询无法翻译的地方。要么以可翻译的形式重写查询,

c# - 表 'DBNAME.dbo.TableNAME' 不存在 MySQL Entity Framework 6

c# - 与 EntityFramework 的命名冲突

c# - 如何以编程方式访问焦点元素 WPF C#

c# - 根据Windows主题颜色wpf更改控件的背景

c# - 使用集合参数对集合属性进行 Linq 查询

C# 添加范围列表<List<T>>

c# - 查询为空时的最大返回值