我要构建 LINQ
稍后将翻译为 WHERE IN
在sql
.在常规用例中,我会这样做:
(querable
是 IQuerable<T>
而 arr
是 IEnumerable<int>
)
querable = querable.Where(e => arr.Contains(e.Id));
但是
我的问题是我要过滤的值 ( e.Id
) 是动态的,我将其作为字符串获取。我该怎么做?
一些背景: 我正在做 REST API 端点,用户可以在其中发送他想要过滤值的列,所以示例是:
-
filter: {"id": [1,2]}
我想将其翻译成类似 queryable.Where(e => new [] {1,2}.Contains(e.Id))
的内容
-
filter: {"customerId": [4,5]}
我想将其翻译成类似 queryable.Where(e => new [] {4,5}.Contains(e.CustomerId))
的内容
所以基本上我的输入是一个列名,它是一个 string
和 ID 列表,即 IEnumerable<int>
我觉得可以用Expression
来实现(类似于 this answer )但我不知道该怎么做。
最佳答案
你可以这样做:
public static class QueryableExtensions {
public static IQueryable<TEntity> WhereIn<TEntity, TValue>(this IQueryable<TEntity> query, string property, IEnumerable<TValue> values) {
// x
var arg = Expression.Parameter(typeof(TEntity), "x");
// x.Property
var prop = Expression.Property(arg, property);
// values.Contains(x.Property)
var contains = Expression.Call(
typeof(Enumerable),
"Contains",
new[] { typeof(TValue) },
Expression.Constant(values),
prop
);
// x => values.Contains(x.Property)
var lambda = Expression.Lambda<Func<TEntity, bool>>(contains, arg);
return query.Where(lambda);
}
}
请注意,您传递的可枚举值类型和属性类型应该匹配才能起作用(因此,如果属性是 int 类型 - 传递 int 数组)。
关于c# - WhereIn 动态属性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47796587/