【问题标题】:Lambda Expression for dynamic Object动态对象的 Lambda 表达式
【发布时间】:2014-12-13 08:37:20
【问题描述】:

我正在尝试为在运行时创建的表构建 Lambda 表达式。 表达式构建良好,但是当我调用 Compile() 方法时出现此错误 “'cseval.Item' 类型的 ParameterExpression 不能用于'System.Object' 类型的委托参数” 这是我的功能

    public Func<dynamic, Boolean> GetWhereExp(List<WhereCondition> SearchFieldList, dynamic item)
    {

        ParameterExpression pe = Expression.Parameter(item.GetType(), "c");

        Expression combined = null;

        if (SearchFieldList != null)
        {
            foreach (WhereCondition fieldItem in SearchFieldList)
            {
                //Expression for accessing Fields name property
                Expression columnNameProperty = Expression.Property(pe, fieldItem.ColumName);


                //the name constant to match 
                Expression columnValue = Expression.Constant(fieldItem.Value);

                //the first expression: PatientantLastName = ?
                Expression e1 = Expression.Equal(columnNameProperty, columnValue);

                if (combined == null)
                {
                    combined = e;
                }
                else
                {
                    combined = Expression.And(combined, e);
                }
            }
        }
        var result = Expression.Lambda<Func<dynamic, bool>>(combined, pe);
        return result.Compile();
    }

【问题讨论】:

  • 我不相信dynamic 允许在Expressions 中使用。我在您的代码中看不到任何看起来实际上需要 dynamic 类型的内容。您是否尝试过将dynamic 替换为object
  • 是的,我试过了,但同样的错误。

标签: c# linq lambda


【解决方案1】:

我已将动态更改为泛型,此代码适用于我:

    public Func<T, Boolean> GetWhereExp<T>(List<WhereCondition> SearchFieldList, T item)
    {
        var pe = Expression.Parameter(item.GetType(), "c");
        Expression combined = null;
        if (SearchFieldList != null)
        {
            foreach (var fieldItem in SearchFieldList)
            {
                var columnNameProperty = Expression.Property(pe, fieldItem.ColumName);
                var columnValue = Expression.Constant(fieldItem.Value);
                var e1 = Expression.Equal(columnNameProperty, columnValue);
                combined = combined == null ? e1 : Expression.And(combined, e1);
            }
        }
        var result = Expression.Lambda<Func<T, bool>>(combined, pe);
        return result.Compile();
    }

小提示:你的方法返回的是函数,而不是表达式,所以'GetWhereExp'这个名字有点不正确。如果你想返回函数,恕我直言,最好使用反射。

UPD:我用这段代码来测试:

            var expressions = new List<WhereCondition>
                {
                    new WhereCondition("Column1", "xxx"),
                    new WhereCondition("Column2", "yyy"),
                };

            var item = new
                {
                    Column1 = "xxx",
                    Column2 = "yyy"
                };

            var func = LinqExpr.GetWhereExp(expressions, (dynamic)item);

            Console.WriteLine(new[] {item}.Count(a => func(a)));

【讨论】:

  • 这里的问题该项目类型是在运行时生成的。所以当我需要调用函数时,我无法传递 T 参数的类型
猜你喜欢
  • 2018-08-07
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-03-04
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多