【问题标题】:InvalidOperationException: No method 'Where' on type 'System.Linq.Queryable' is compatible with the supplied argumentsInvalidOperationException:类型“System.Linq.Queryable”上没有方法“Where”与提供的参数兼容
【发布时间】:2010-08-06 11:21:19
【问题描述】:

(以下代码已更新并正常运行)

有来自 LinqPad 的动态 OrderBy 示例。我想要做的只是简单地为这个样本应用“Where”而不是“OrderBy”。这是我的代码:

    IQueryable query =            
    from p in Purchases
    //where p.Price > 100
    select p;

string propToWhere = "Price"; 

ParameterExpression purchaseParam = Expression.Parameter (typeof (Purchase), "p");
MemberExpression member = Expression.PropertyOrField (purchaseParam, propToWhere);

Expression<Func<Purchase, bool>> lambda = p => p.Price < 100;
lambda.ToString().Dump ("lambda.ToString");


//Type[] exprArgTypes = { query.ElementType, lambda.Body.Type };
Type[] exprArgTypes = { query.ElementType };

MethodCallExpression methodCall =
    Expression.Call (typeof (Queryable), "Where", exprArgTypes, query.Expression, lambda);

IQueryable q = query.Provider.CreateQuery (methodCall);
q.Dump();
q.Expression.ToString().Dump("q.Expression");

此代码出现异常: “InvalidOperationException:‘System.Linq.Queryable’类型上的‘Where’方法没有与提供的参数兼容。”

任何帮助都会被评估。

干杯

【问题讨论】:

    标签: c# linq linqpad


    【解决方案1】:

    您创建的 lambda 表达式对我来说看起来很奇怪。您无缘无故地添加了另一个参数。您还使用Predicate&lt;Purchase&gt; 而不是Func&lt;Purchase, bool&gt;。试试这个:

    LambdaExpression lambda = Expression.Lambda<Func<Purchase, bool>>(
                        Expression.GreaterThan(member, Expression.Constant(100)), 
                        purchaseParam);
    

    【讨论】:

    • 您好乔恩,感谢您的回复。您提供的表达式抱怨“没有为类型 'System.Decimal' 和 'System.Int32' 定义二元运算符 GreaterThan。”
    • 啊。您没有明确指出 Price 是小数。我怀疑最简单的解决方案是将 100 更改为 100m。
    【解决方案2】:
    1. 使用 Jon Skeet 提供的 lambda。或许他也能解释一下为什么ParameterExpression用起来那么痛苦,需要使用相同的实例,而不是能够通过名字来匹配:)

    2. 修改这一行:

    Type[] exprArgTypes = { query.ElementType };
    

    exprArgTypes 是类型参数

    IQueryable<TSource> Where<TSource>(this IQueryable<TSource> source, Expression<Func<TSource, bool>> predicate).
    

    如您所见,它只有一个类型参数——TSource,即Purchase。你正在做的,实际上是用两个类型参数调用Where 方法,如下所示:

    IQueryable<Purchase> Where<Purchase, bool>(this IQueryable<Purchase> source, Expression<Func<Purchase, bool>> predicate)
    

    一旦这两个修复都在表达式中运行就没有问题了。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2019-11-08
      • 1970-01-01
      • 2022-11-24
      • 1970-01-01
      • 2019-06-18
      • 1970-01-01
      • 2018-09-07
      相关资源
      最近更新 更多