不能在表达式树的lambda中使用动态委托参数

时间:2015-02-10 16:36:05

标签: c# lambda

我正在尝试在动态选择的表上应用简单的“Where”子句。但是,将应用于子句的表字段也是动态的,我无法弄清楚如何使该部分工作。使动态表正常工作。

using (var context = new DBEntities())
{
    var type = context.GetType();
    var tableProperty = type.GetProperty("tableName");
    var tableGet = tableProperty.GetMethod;
    var tableContent = tableGet.Invoke(context, null);
    var tableQuery = (IQueryable)tableContent;
    var tableType = tableQuery.ElementType;

    var pe = Expression.Parameter(tableType, "tableType");
    var left = Expression.PropertyOrField(pe, "fieldName");
    var right = Expression.Constant("fieldValue");
    var predicateBody = Expression.Equal(left, right);

    var whereCallExpression = Expression.Call(typeof(Queryable), "Where", new[] { tableType },
        tableQuery.Expression, Expression.Lambda<Func<tableType, bool>>(predicateBody, pe));

    IQueryable<string> results = tableQuery.Provider.CreateQuery<string>(whereCallExpression);
}

由于Expression.Lambda<Func<tableType, bool>>(predicateBody, pe),此代码块无法编译。如果我对表达式相关代码的类型进行硬编码,则此示例将运行并返回预期结果。

1 个答案:

答案 0 :(得分:1)

代码无法编译,因为tableType(类型为System.Type的变量)不能用作泛型函数的类型参数。

但是,您应该能够通过调用非通用Lambda<Func<...>>替换对通用Lambda的调用来进行编译和运行:

var whereCallExpression = Expression.Call(typeof(Queryable), "Where", new[] { tableType },
    tableQuery.Expression, Expression.Lambda(predicateBody, pe));