C# 将LINQ中的多个where子句连接为或代替AND
是否仍有将LINQ where子句作为或加入C# 将LINQ中的多个where子句连接为或代替AND,c#,linq,C#,Linq,是否仍有将LINQ where子句作为或加入 var ints = new [] { 1, 3, 5, 7 }; var query = from i in ints select i; query = query.Where (q => q == 3); query = query..Where (q => q == 7); 我想要的是动态添加where子句的能力,但要使它们使用OR而不是AND您是说在lambda中指定多个条件吗 query = query.Where(q
var ints = new [] { 1, 3, 5, 7 };
var query = from i in ints select i;
query = query.Where (q => q == 3);
query = query..Where (q => q == 7);
我想要的是动态添加where子句的能力,但要使它们使用OR而不是AND您是说在lambda中指定多个条件吗
query = query.Where(q => q == 3 ||
q == 7);
试试这个
var ints=new[]{1,3,5,7}代码>
var query=ints.select(X=>X).其中(X=>X==3 | | X==7)代码>如果您想继续使用强类型Linq查询,您应该查看LinqKit和谓词构建。我用它做了一些类似的事情,发现它可以很好地处理和/或堆叠过滤器
有关更深入的信息,请查看。下面是我代码中的一个片段:
//Setup the initial predicate obj then stack on others:
basePredicate = basePredicate.And(p => false);
var predicate1 = PredicateBuilder.True<Person>();
foreach (SearchParms parm in parms)
{
switch (parm.field)
{
case "firstname":
predicate1 = predicate1.And(p => p.FirstName.Trim().ToLower().Contains(sValue));
break;
//etc...
}
}
//Run a switch based on your and/or parm value to determine stacking:
if (Parm.isAnd) {
basePredicate = basePredicate.And(predicate1);
} else {
basePredicate = basePredicate.Or(predicate1);
}
//设置初始谓词obj,然后在其他对象上堆叠:
basePredicate=basePredicate.And(p=>false);
var predicate1=PredicateBuilder.True();
foreach(SearchParms parm in parms)
{
开关(参数字段)
{
案例“名字”:
predicate1=predicate1.And(p=>p.FirstName.Trim().ToLower().Contains(sValue));
打破
//等等。。。
}
}
//根据您的和/或parm值运行开关以确定堆叠:
如果(按isAnd参数){
basePredicate=basePredicate.And(谓词1);
}否则{
basePredicate=basePredicate.Or(谓词1);
}
像这样的东西怎么样
var query = from i in ints where CheckConditions(i) select i;
public bool CheckConditions(int i)
{
var conditions = WhereConditions; //an IEnumerable<Func<int, bool>> of dynamically added conditions
foreach (var condition in conditions)
{
if (condition(i)) return true;
}
return false;
}
var query=ints中的from i,其中CheckConditions(i)选择i;
公共布尔检查条件(int i)
{
var conditions=WhereConditions;//动态添加的条件的IEnumerable
foreach(条件中的var条件)
{
如果(条件(i))返回true;
}
返回false;
}
你可以把它扩展到更聪明一点,但我就是这么做的
编辑:很抱歉,第一个示例是和,现在已将其更改为或。因此,当它第一次遇到传递条件时,它将返回true。使用ExpressionVisitor
帮助在具有或/和关系的两个表达式的基础上构建表达式。这个答案来自于
内部类参数replacer:ExpressionVisitor
{
公共参数置换器(参数表达式参数置换器)
{
this.ParameterExpression=parameterxpr;
}
公共参数表达式参数表达式{get;private set;}
公共表达式替换(表达式表达式表达式)
{
回访(expr);
}
受保护的重写表达式VisitParameter(ParameterExpression p)
{
返回this.ParameterExpression;
}
}
公共静态表达式和(此表达式一个,表达式另一个)
{
var candidateExpr=Expression.Parameter(typeof(T),“candidate”);
var parameterReplacer=新的parameterReplacer(candidateExpr);
var left=参数更换器更换(一个主体);
var right=参数replacer.Replace(另一个主体);
var body=表达式和(左、右);
返回表达式.Lambda(body,candidatexpr);
}
公共静态表达式或(此表达式,一个表达式,另一个表达式)
{
var candidateExpr=Expression.Parameter(typeof(T),“candidate”);
var parameterReplacer=新的parameterReplacer(candidateExpr);
var left=参数更换器更换(一个主体);
var right=参数replacer.Replace(另一个主体);
变量体=表达式。或(左、右);
返回表达式.Lambda(body,candidatexpr);
}
我正在尝试做类似的事情。以下是我的想法:
//various test cases
bool useTestCase1 = true;
bool useTestCase2 = true;
bool useTestCase3 = false;
query = query.Where(q =>
(q == 3 && useTestCase1 ) ||
(q == 7 && useTestCase2 ) ||
(q == 10 && useTestCase3 )
);
您可以使用Union方法:
var ints = new [] { 1, 3, 5, 7 };
var query = ints.Where(q => q == 3);
query = query.Union(ints.Where(q => q == 7));
这仍然不是动态的解决方案。是的,听起来像是一条路要走——或者他可以使用DLINQ?有趣的解决方案。我们正在寻找一种没有单独lib的方法,但为什么要重新发明轮子:)即使从linqKit开始,也不要担心,对于使用此方法的特定解决方案,仍有许多代码需要“发明”。
var ints = new [] { 1, 3, 5, 7 };
var query = ints.Where(q => q == 3);
query = query.Union(ints.Where(q => q == 7));