List< object>中的实体框架动态where子句; [英] Entity Framework Dynamic Where Clause from List<object>

查看:121
本文介绍了List< object>中的实体框架动态where子句;的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在搜寻互联网之后,我找不到能够上班的解决方案.我正在尝试使用动态linq来使用户能够从Windows窗体构建自定义查询.为了容纳每个where子句,我构建了一个名为WhereClause的对象:

After scourging the internet I have not been able to find a solution that i can get to work. I am attempting to use dynamic linq to enable the user to build a custom query from a windows form. To hold each where clause I have built an object called WhereClause:

public class WhereClause
{
    public int id { get; set; }
    public string ColumnName { get; set; }
    public string Operator { get; set; }
    public string OperatorSymbol { get; set; }
    public object Value { get; set; }
    public string AndOr { get; set; }
    public string AndOrSymbol { get; set; }
}

多数是不言自明的,但运算符和运算符之间的区别在于,运算符会将等于"或大于"存储到运算符符号分别为"=="和>"的位置. AndOR的工作方式与此类似.

Most is self explanatory, but the distinction between Operator and Operator Symbol is that the Operator will store "Equals" or "Greater Than" to where the Operator Symbol will be "==" and ">" respectively. The AndOR works in a similar fashion.

然后,当用户构建where子句时,将创建一个新的WhereClause对象并将其添加到List<WhereClause>

Then as the user builds the where clauses a new WhereClause object is created and added to a List<WhereClause>

当需要运行查询时,我正在使用实体框架和linq来构建查询.

When it comes time to running the query I am using entity framework and linq to build the query.

我想做类似的事情:

List<WhereClause> wheres; //populated via parameter in the encapsulating method.

DataContext db = new DataContext();
var query = from d in db.Database select d;

string whereClause = "";

foreach(WhereClause where in wheres){
    whereClause = whereClause + String.Format(" {0} {1} {2} {3}", where.ColumnName, where.OperatorSymbol, where.Value, where.AndOrSymbol);

    query.Where(whereClause);

}

我已经尝试了各种方式来构建where子句,包括使用where(predicate, params)和使用"@1"格式化谓词,但是还没有找到正确的方法.

Ive tried every which way to build the where clauses including using the where(predicate, params) and formating the predicate using "@1" but havent found the right way to do so.

这是上下文的查询生成器的外观.

Here is what the query builder looks like for context..

所以现在我向你们寻求帮助.

So now I turn it to you guys for help..

推荐答案

您需要将WhereClause对象转换为Expression,然后才能将其用作where查询.这里是一个例子:

You need to translate your WhereClause object into Expression, then you can use it as where query. Here an example:

Type yourType = typeof(YourGeneric);
ParameterExpression pe = Expression.Parameter(yourType , "x");
Expression left = Expression.Property(pe, yourType.GetProperty(whereClause.ColumnName));
Expression right = Expression.Constant(whereClause.Value, typeof(int));
Expression result = Expression.Equal(left, right);

这是一个比较int属性的示例.您需要一些if(或切换)来了解属性类型以及需要进行的比较类型.

This is an example to compare an int property. You need some if (or switch) to understand property type and what type of comparation you need to do.

if (whereClause.Operator == "Greater Than") {
    result = Expression.GreaterThan(left, right);
}

当您以这种方式使用Expression后:

When you finished use Expression in this way:

context.Set<YourGeneric>().Where(result);

我建议使用泛型(如果可能)来简化代码和工作. 您还可以连接更多表达式:

I reccomend to use generics (if possible) to simplify code and work. You can also concatenate more expressions:

Expression result4 = Expression.AndAlso(result1, result2);
Expression finalRes = Expression.Or(result3, result4);

这篇关于List&lt; object&gt;中的实体框架动态where子句;的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆