小编典典

如何动态组合linq查询?

sql

假设我有一个表,在字符串(nvarchar)列中包含格式化的值。这些值应该是由某些const符号分隔的字符串(让它是分号;)。例如,

12;0;5;dog //four values separated by a semi-colon

或者

053 //if there is only one value, no semi-colon at the end

分隔符始终是分隔符,不能是值的一部分。

我需要检查该表中是否已经有一行,并且该列中的值列表至少包含指定的一项。换句话说,我有一个值列表:

List<string> list = new List<string>() { "somevalue1", "somevalue2" };

分隔符:

string separator = ";";

我需要编写一个执行此操作的linq-to-sql查询:

select ... from sometable
where Value='somevalue1' or Value like 'somevalue1;%' or
      Value like '%;somevalue1' or Value like '%;somevalue1;%'

   or Value='somevalue2' or Value like 'somevalue2;%' or 
      Value like '%;somevalue2' or Value like '%;somevalue2;%'

应该提到的是,任何搜索值都可以包含其他值。也就是说,我可能正在精确搜索5,而某行可能包含1;15;55。这样的行 不能
匹配。While...;5;...或just 5,或5;...或是...;5匹配项。

使用linq-to sql我知道如何进行以下类型的查询:

select ... from sometable where (... or ... or ...) and (... or ...) ...

那是

IQueryable<SomeTable> query = dc.SomeTable;
foreach (string l in list)
{
    string s = l;
    query = query.Where(b => b.Value.StartsWith(s + separator) ||
                             b.Value.EndsWith(separator + s) ||
                             b.Value.Contains(separator + s + separator) ||
                             b.Value.Equals(s));
}
if (query.Any()) {/*...*/}

显然,这些Where语句AND在生成的sql查询中加入了,而我却OR无所不在。

那么有没有办法在C#代码中获取我需要的查询?还是唯一的方法是使用手写查询和DataContext.ExecuteQuery方法来执行此操作?


阅读 172

收藏
2021-04-14

共1个答案

小编典典

我想一个UNION将满足您的需求:

IQueryable<SomeTable> baseQuery = dc.SomeTable;
IQueryable<SomeTable> query = new List<SomeTable>().AsQueryable();
foreach (string l in list)
{
    string s = l;

    query.Union(baseQuery.Where(b => b.Value.StartsWith(s + separator) ||
                             b.Value.EndsWith(separator + s) ||
                             b.Value.Contains(separator + s + separator) ||
                             b.Value.Equals(s)));
}
if (query.Any()) {/*...*/}
2021-04-14