我有一種情況,我需要爲查詢的左側和右側動態生成LINQ查詢。換句話說,Where(「some property == some value」)。我在LINQPad中玩弄了PredicateBuilder,並嘗試了其他一些東西,但最終LINQ動態查詢庫(System.Linq.Dynamic)使這項任務變得非常簡單。
沒有經過所有的細節,我有一個方法,它需要在MVC頁面上的jqGrid上過濾和排序項目的參數。名爲QueryOptions的對象包含各種查詢設置。 Data.ImportDataSearchView是綁定到後端數據庫視圖的實體框架實體。
過濾器表達式是通過調用建立:
options.FilterExpression += filterList.BuildFilterExpression<Data.ImportDataSearchView>();
BuildFilterExpression的部分如下:,
public string BuildFilterExpression<T>()
{
var type = typeof(T);
var exp = string.Empty;
foreach (Filter filter in this)
{
var typeName = filter.DataType.ToLower();
// Skip if no values
if (!filter.Values.Any())
continue;
switch (typeName)
{
case "string":
// html decode string and escape single quotes
var stringVal = System.Web.HttpUtility.HtmlDecode(filter.Values[0]);
stringVal = stringVal.Replace("'", "''");
if (filter.Operator == Enums.FilterOperator.CONTAINS)
exp += string.Format("{0}.Trim().ToLower().Contains(\"{1}\")", filter.Attribute, stringVal.Trim().ToLower());
else if (filter.Operator == Enums.FilterOperator.DOES_NOT_EQUAL)
exp += string.Format("!{0}.ToLower().Equals(\"{1}\")", filter.Attribute, stringVal.ToLower());
else if (filter.Operator == Enums.FilterOperator.DOES_NOT_CONTAIN)
exp += string.Format("!{0}.Trim().ToLower().Contains(\"{1}\")", filter.Attribute, stringVal.Trim().ToLower());
else if (filter.Operator == Enums.FilterOperator.ENDS_WITH)
exp += string.Format("{0}.Trim().ToLower().EndsWith(\"{1}\")", filter.Attribute, stringVal.Trim().ToLower());
else if (filter.Operator == Enums.FilterOperator.EQUALS)
exp += string.Format("{0}.ToLower().Equals(\"{1}\")", filter.Attribute, stringVal.ToLower());
else if (filter.Operator == Enums.FilterOperator.STARTS_WITH)
exp += string.Format("{0}.Trim().ToLower().StartsWith(\"{1}\")", filter.Attribute, stringVal.Trim().ToLower());
break;
//case "select": -- for dropdowns
//case "datetime": -- for dates, etc. etc.
// add spaces around expression
exp = string.Format(" {0} ", exp);
// add and/or to expression
if (this.IndexOf(filter) != this.Count() - 1)
exp += string.Format(" {0} ", ExpressionType.ToLower() == "and" ? "&&" : "||");
}
return exp;
}
然後數據被檢索如下建立表達串後:
options.OrderBy = string.IsNullOrEmpty(sortIndex) ? "TrackingId asc" : string.Format(" {0} {1} ", sortIndex, sortOrder);
var db = new Data.BmpDB();
var list = string.IsNullOrEmpty(options.FilterExpression)
? db.ImportDataSearchViews.OrderBy(options.OrderBy).ToList()
: db.ImportDataSearchViews.Where(options.FilterExpression).OrderBy(options.OrderBy).ToList();
下面的options.FilterExpression字符串是t通過該方法BuildFilterExpression拼湊成一個好的,簡單謂詞字符串爲重稀土LINQ搜索條件字段where子句:
「BmpName.Trim()ToLower將()包含(\」 作物\「)& & DataProviderId。降低()。等於(\「123 \」)& & StatusId == 1"
你能在我的答案提供反饋?我覺得應該是足夠好回答或瀏覽你想要的解決方案。 –