近日在使用了一下EF框架,在做多条件where查询的时候不知道怎么做,网上找了找,一开始用context.Database.SqlQuery<T>方法写sql语句,之后遇到了SqlParamterCollection已在另一定义的问题,找了一下,大概知道什么问题,觉得用EF真的有点不方便,还不如用Dapper开发效率快,之后又在网上搜了搜关键字EF框架多条件Where查询就打开了新世界的大门。动态创建lambda表达式,我跟着学习了一下写的
代码如下:
//querydata 是Dictionary<string,string> 放着要查询的属性名和相应的值
ParameterExpression pe = Expression.Parameter(typeof(Customer), "customer");//lambda表示式里的参数我这边是单参数
Expression left;//相当于 a=b 的 a
Expression right;//相当于a=b 的 b
Expression e;//作为最后形成的表达式的载体
//先放一个初始值后面被替换不然循环里不方便用
left = Expression.Property(pe, typeof(Customer).GetProperty("name"));//Customer.name
right = Expression.Constant("巅峰白杨");//Constant方法设置属性对应的值
e = Expression.Equal(left, right);//Customer.name=="巅峰白杨"
//循环查询条件字典
foreach (var item in querydata)
{
if (!item.Value.ToString().Trim().Equals(""))
{
left = Expression.Property(pe, typeof(SFC_Package).GetProperty(item.Key));
right = Expression.Constant(item.Value);
if (index == 0)
{
e = Expression.Equal(left, right);
index++;
}
else
{
if (e != null)
{
Expression tempe;
tempe = Expression.Equal(left, right);
e = Expression.And(tempe, e);//加了一个&&连接两个判断
}
}
}
}
IQueryable<Customer> queryableData = db.Customer.AsQueryable<Customer>();//将IEnumerable类型转成IQueryable
//Where方法的lambda表达式
MethodCallExpression whereCallExpression = Expression.Call(
typeof(Queryable),
"Where",
new Type[] { queryableData.ElementType },
queryableData.Expression,
Expression.Lambda<Func<SFC_Package, bool>>(e, new ParameterExpression[] { pe }));
//OrderBy方法的lambda表达式 这边写的有点冗余第一次写不太习惯,想想重复了很多
var propertyinfo=typeof(Customer).GetProperty("Name");
Expression body=Expression.Property(pe,propertyinfo);
Type nametype=propertyinfo.PropertyType;
MethodCallExpression orderByCallExpression = Expression.Call(
typeof(Queryable),
"OrderBy",
new Type[] { queryableData.ElementType, nametype},//其实可以写成queryableData.ElementType.GetProperty("Name").PropertyType
whereCallExpression,
Expression.Lambda(body, pe));
//使用已创建好的lambda表达式查询数据 ps:IQueryable和IEnumerable可以转换方便处理查询结果
IQueryable<SFC_Package> results = queryableData.Provider.CreateQuery<Customer>(orderByCallExpression);
网上还看到一种简单的多条件查询的方法,相当于
var data=db.Customer.Where(o=>o.name=="西门吹雪");
data=data.Where(o=>o.sex="男神")
用循环来多次Where实现多条件查询,感觉可能会造成多次数据库查询,不过用在Linq to Object
上应该挺好的。