我想有3-4个搜索选项。现在我在If语句中使用我的查询。
if inputcol1 > 0 And Not inputCol2 = "" then
Dim list = (From P In db.table
Where P.column1 = inputCol1 and P.column2 = inputCol2
Select P).ToList()
end if
和一个(或4个)更多的另一个条件但几乎相同的查询,只有一个不同的where子句。所以这个查询简化而且简短。因此,如果我有一个非常大的查询,那将是一个很大的混乱。我不希望其他程序员只为几个选项阅读这么多代码。
是否有一种简单的方法可以查看是否填写了搜索选项并进行查询?
答案 0 :(得分:1)
现在已经晚了,但是我目前正在VB.NET项目上工作,除了Gert Arnold的answer之外,在选择i-e中具有相同的对象也很重要。链接时使用P,因为例如如果说P是项目实体,并且在最终结果中(过滤后),您正在选择其他列或对象详细信息,例如query = (From P in query Select P.Name, P.Deadline)
,则它将引发类型转换异常,因为变量query
与Select P.Name, P.Deadline
的结构或对象不同。因此,如果要在最终选择中具有不同的结构,请使用另一个变量,例如:
Dim query = (From P in query Where P.Col2 = inputCol2 Select P)
Dim result = From P In query Select P.Name, P.Deadline ...
'and then displaying it
DataGridView.DataSource = result.toList()
但是,我确实尝试通过result = From P in query Select New With {P.Name, P.Deadline}
创建一个New Type,但是没有用。我不知道为什么,如果我有空的话就去研究它。
答案 1 :(得分:0)
您可能想尝试LinqKit。使用此库,您有一个PredicateBuilder
类,其中包含方法:
public static Expression<Func<T, bool>> True<T>();
public static Expression<Func<T, bool>> False<T>();
public static Expression<Func<T, bool>> Or<T>(this Expression<Func<T, bool>> expr1, Expression<Func<T, bool>> expr2);
public static Expression<Func<T, bool>> And<T>(this Expression<Func<T, bool>> expr1, Expression<Func<T, bool>> expr2);
这些是Expression
个对象的扩展,可以从lambdas轻松创建。
通过这样的表达式,您可以yourDataSource.Where(expression)
。
抱歉c#表示法,我不知道VB.net ... 如果有人想把它修复到VB,请随意。
编辑:
嗯,PredicateBuilder
只是一个巧妙的语法糖。在他们的网站上,您可以找到非常简单的完整源代码。不幸的是,在C#中。
在这里:
using System;
using System.Linq;
using System.Linq.Expressions;
using System.Collections.Generic;
public static class PredicateBuilder
{
public static Expression<Func<T, bool>> True<T> () { return f => true; }
public static Expression<Func<T, bool>> False<T> () { return f => false; }
public static Expression<Func<T, bool>> Or<T> (this Expression<Func<T, bool>> expr1,
Expression<Func<T, bool>> expr2)
{
var invokedExpr = Expression.Invoke (expr2, expr1.Parameters.Cast<Expression> ());
return Expression.Lambda<Func<T, bool>>
(Expression.OrElse (expr1.Body, invokedExpr), expr1.Parameters);
}
public static Expression<Func<T, bool>> And<T> (this Expression<Func<T, bool>> expr1,
Expression<Func<T, bool>> expr2)
{
var invokedExpr = Expression.Invoke (expr2, expr1.Parameters.Cast<Expression> ());
return Expression.Lambda<Func<T, bool>>
(Expression.AndAlso (expr1.Body, invokedExpr), expr1.Parameters);
}
}
就是这样!表达式(在.net中是标准的,不需要额外的库)提供了一些很好的方法来处理它们,它们可以在where
子句中使用。
试一试:)
答案 2 :(得分:0)
您使用代码进入正确的轨道......您只需更改Ternary Operator的if语句:
Dim table = New Dictionary(Of Integer, String)
table.Add(1, "one")
table.Add(2, "two")
table.Add(3, "three")
Dim inputCol1 As Integer
Dim inputCol2 As String = "one"
Dim list = (From P In table Where _
(inputCol1 < 1 OrElse P.Key = inputCol1) _
And (inputCol2 = "" OrElse P.Value = inputCol2) _
Select P).ToList()
在此问题上查找有关此情况的更多信息:Conditional filtering
答案 3 :(得分:0)
最好的方法是有条件地扩展您的查询:
Dim query = (From P In db.table Select P)
If inputCol1.HasValue
query = (From P in query Where P.column1 = inputCol1 Select P)
End If
If inputCol2.HasValue
query = (From P in query Where P.inputCol2 = inputCol2 Select P)
End If
' And so on...
Dim list = query.ToList()
使用Not inputCol2.HasValue OrElse P.Value = inputCol2
进行条件筛选将创建一个包含无用谓词的查询。通过有条件地扩展您的查询,只会合并重要的谓词。