Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/linq/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# Linq使用或动态附加Where子句_C#_Linq_Entity Framework_Entity Framework 5 - Fatal编程技术网

C# Linq使用或动态附加Where子句

C# Linq使用或动态附加Where子句,c#,linq,entity-framework,entity-framework-5,C#,Linq,Entity Framework,Entity Framework 5,我一直在尝试使用动态添加的where子句构建linq查询。我有一个网页,其中包含一组复选框,这些复选框被选中以对应于您要搜索的字段: 到目前为止,我掌握的情况如下: //This calls a select from table to construct the query which the where clauses will be added to IQueryable<AutoCompleteRestultDto> query = GetAutocompleteResul

我一直在尝试使用动态添加的where子句构建linq查询。我有一个网页,其中包含一组复选框,这些复选框被选中以对应于您要搜索的字段:

到目前为止,我掌握的情况如下:

//This calls a select from table to construct the query which the where clauses will be added to
IQueryable<AutoCompleteRestultDto> query = GetAutocompleteResults();

if (FirstName == true || AllFields == true)
{
    Expression<Func<AutoCompleteRestultDto, bool>> firstNameFilter = c => terms.Any(t => c.FirstName.ToLower().Contains(t.ToLower()));
    query = query.Where(firstNameFilter);
}
if (LastName == true || AllFields == true)
{
    Expression<Func<AutoCompleteRestultDto, bool>> lastNameFilter = c => terms.Any(t => c.LastName.ToLower().Contains(t.ToLower()));
    query = query.Where(lastNameFilter);
}
if (KnownAs == true || AllFields == true)
{
    Expression<Func<AutoCompleteRestultDto, bool>> knownAsFilter = c => terms.Any(t => c.KnownAs.ToLower().Contains(t.ToLower()));
    query = query.Where(knownAsFilter);
}
// etc.

return query
       .Select(c => new ContactAutoCompleteModel
                {
                    label = c.FirstName + " " + c.LastName
                })
                .Take(15)
                .OrderBy(d => d.label)
                .ToList();
//这将调用select from表来构造将添加where子句的查询
IQueryable query=GetAutocompleteResults();
if(FirstName==true | | AllFields==true)
{
表达式firstNameFilter=c=>terms.Any(t=>c.FirstName.ToLower().Contains(t.ToLower());
query=query.Where(firstNameFilter);
}
if(LastName==true | | AllFields==true)
{
表达式lastNameFilter=c=>terms.Any(t=>c.LastName.ToLower().Contains(t.ToLower());
query=query.Where(lastNameFilter);
}
if(KnownAs==true | | AllFields==true)
{
表达式knownAsFilter=c=>terms.Any(t=>c.KnownAs.ToLower().Contains(t.ToLower());
query=query.Where(knownAsFilter);
}
//等等。
返回查询
.选择(c=>new ContactAutoCompleteModel
{
label=c.FirstName+“”+c.LastName
})
.Take(15)
.OrderBy(d=>d.label)
.ToList();
问题是这个解决方案要求附加的所有表达式同时为真,即:where(第1条、第2条和第3条)


无法确定如何将此更改为或子句,即:where(第1条或第2条或第3条)

您正在链接可枚举的
。where
调用您发布的代码。这就是为什么你会得到这样的效果。下面是使用谓词而不是表达式的
PredicateBuilder

  public static class PredicateExtensions
  {
    public static Predicate<T> Or<T> (this Predicate<T> p1, Predicate<T> p2)
    {
      return obj => p1(obj) || p2(obj);
    }

    public static Predicate<T> And<T> (this Predicate<T> p1, Predicate<T> p2)
    {
      return obj => p1(obj) && p2(obj);
    }
    public static Predicate<T> False<T> () { return obj => false; }
    public static Predicate<T> True<T>  () { return obj => true; }

    public static Predicate<T> OrAll<T> (IEnumerable<Predicate<T>> conditions)
    {
      Predicate<T> result = PredicateExtensions.False<T>();
      foreach (Predicate<T> cond in conditions)
        result = result.Or<T>(cond);
      return result;
    }

    public static Predicate<T> AndAll<T> (IEnumerable<Predicate<T>> conditions)
    {
      Predicate<T> result = PredicateExtensions.True<T>();
      foreach (Predicate<T> cond in conditions)
        result = result.And<T>(cond);
      return result;
    }
  }
公共静态类谓词扩展
{
公共静态谓词Or(此谓词p1,谓词p2)
{
返回obj=>p1(obj)| | p2(obj);
}
公共静态谓词和(此谓词p1,谓词p2)
{
返回obj=>p1(obj)和p2(obj);
}
公共静态谓词False(){return obj=>False;}
公共静态谓词True(){return obj=>True;}
公共静态谓词OrAll(IEnumerable条件)
{
谓词结果=PredicateExtensions.False();
foreach(条件中的谓词cond)
结果=结果或(cond);
返回结果;
}
公共静态谓词AndAll(IEnumerable条件)
{
谓词结果=PredicateExtensions.True();
foreach(条件中的谓词cond)
结果=结果和(cond);
返回结果;
}
}
您可以将上述类似方法用于可枚举项,在某些条件下自定义(apriori)谓词可枚举项:

Predicate<AutoCompleteRestultDto> firstNamePredicate = 
    c => terms.Any(t => c.FirstName.ToLower().Contains(t.ToLower()));
Predicate<AutoCompleteRestultDto> lastNamePredicate = 
    c => terms.Any(t => c.LastName.ToLower().Contains(t.ToLower()));
Predicate<AutoCompleteRestultDto> knownAsPredicate = 
    c => terms.Any(t => c.KnownAs.ToLower().Contains(t.ToLower()));
var all = new Predicate<AutoCompleteRestultDto>[] { 
    firstNamePredicate, 
    knownAsPredicate, 
    lastNamePredicate };
//
var items = query.Where(a => PredicateExtensions.OrAll(all)(a)).ToList();
items = query.Where(a => PredicateExtensions.AndAll(all)(a)).ToList();
谓词firstNamePredicate=
c=>terms.Any(t=>c.FirstName.ToLower().Contains(t.ToLower());
谓词lastNamePredicate=
c=>terms.Any(t=>c.LastName.ToLower().Contains(t.ToLower());
谓词knownAsPredicate=
c=>terms.Any(t=>c.KnownAs.ToLower().Contains(t.ToLower());
var all=新谓词[]{
名字谓词,
知道谓词,
lastNamePredicate};
//
var items=query.Where(a=>predicteextensions.OrAll(all)(a)).ToList();
items=query.Where(a=>PredicateExtensions.AndAll(all)(a)).ToList();
或者像您这样一步一步地迭代添加它们:

Predicate<AutoCompleteRestultDto> orResultPredicate = 
    PredicateExtensions.False<AutoCompleteRestultDto>();
if (FirstName == true || AllFields == true) {
    orResultPredicate=orResultPredicate.Or(firstNamePredicate); } 
if (LastName == true || AllFields == true) { 
    orResultPredicate = orResultPredicate.Or(lastNamePredicate); }
if (KnownAs == true || AllFields == true) { 
    orResultPredicate = orResultPredicate.Or(knownAsPredicate); }
Func<AutoCompleteRestultDto, bool> funcOr = c => orResultPredicate(c);
//
IQueryable<AutoCompleteRestultDto> query; // initialized already
var items = query.Where(funcOr).ToList(); 
谓词或ResultPredicate=
PredicateExtensions.False();
if(FirstName==true | | AllFields==true){
orResultPredicate=orResultPredicate.Or(firstNamePredicate);}
如果(LastName==true | | AllFields==true){
orResultPredicate=orResultPredicate.Or(lastNamePredicate);}
如果(KnownAs==true | | AllFields==true){
orResultPredicate=orResultPredicate.Or(knownAsPredicate);}
Func funcOr=c=>orResultPredicate(c);
//
IQueryable查询;//已初始化
var items=query.Where(funcOr.ToList();

您尝试过PredicateBuilder吗?