在where子句中构建动态linq查询
本文关键字:动态 linq 查询 构建 where 子句 | 更新日期: 2023-09-27 18:27:19
我想构建一个动态查询,如果对象的值不是空字符串,则该查询能够扩展where子句条件。这是代码
public IEnumerable<Filter> GetFilter(Filter filter)
{
var y = ConditionalAttribute(filter);
var query =
from sub in Subscriptions
join u in Users
on sub.UserID equals u.Id
join od in Order_Details1
on sub.OD_Id equals od.OD_Id
join p in Products
on od.ProductId equals p.ProductId
where p.Type == "Testing" + y
select new Filter
{
//do something
};
对于Filter对象,这是代码
public class Filter
{
public int UserId { get; set; }
public string FirstName { get; set;}
}
这个想法是如果过滤器。FirstName不为空,它将像下面的一样附加where子句
public String ConditionalAttribute(Filter filter)
{
if(filter.FirstName != "")
return "&& u.First_Name = " + filter.FirstName + "";
}
有没有办法像上面的代码一样,一个字符串一个字符串地附加where子句?因为我已经尝试了上面的方法,但它失败了,这要归功于
创建尽可能多的动态项,以便在返回IQueryable的小方法中使用。
public IQueryable ConditionalAttribute(IQueryable query, Filter filter)
{
if(filter.FirstName != "") {
query = query.Where(x => x.First_Name == filter.FirstName);
}
return query;
}
然后根据需要在初始LINQ语句之后应用它们:
public IEnumerable<Filter> GetFilter(Filter filter)
{
var query =
from sub in Subscriptions
join u in Users
on sub.UserID equals u.Id
join od in Order_Details1
on sub.OD_Id equals od.OD_Id
join p in Products
on od.ProductId equals p.ProductId
where p.Type == "Testing"
select new Filter
{
//do something
};
query = ConditionalAttribute(query, filter);
除非您使用.ToList()或FirstOrDefault()或类似的方法将语句投影到中,否则该语句不会运行,因此您可以根据需要多次以这种方式链接到查询。
我倾向于使用标准的C#语法,而不是LINQ语法,但话虽如此,我发现在连接查询时,LINQ语法更优雅。
这里有一种方法,它利用标准的C#语法来动态过滤源容器,然后使用LINQ语法来创建联接查询。
public IEnumerable<Filter> GetFilter(Filter filter)
{
var y = ConditionalAttribute(filter);
IEnumerable<User> filteredUsers = Users;
if(!string.IsNullOrEmpty(filter.FirstName))
{
filteredUsers = filteredUsers.Where(u => u.First_Name == filter.FirstName);
}
var query =
from sub in Subscriptions
join u in filteredUsers
on sub.UserID equals u.Id
join od in Order_Details1
on sub.OD_Id equals od.OD_Id
join p in Products
on od.ProductId equals p.ProductId
where p.Type == "Testing" + y
select new Filter
{
//do something
};