2011-11-17 99 views
5

我正在使用Dynamic LINQ Library进行筛选的大型应用程序。使用动态LINQ在子查询上进行筛选

所有我的数据访问层中的类都从一个共同的祖先DALAncestor其中,除其他事项外,定义方法的GetData导出:公共抽象列表的GetData(过滤器过滤)

用于该方法的一个实施一个客户是这样的(简化):

public override List<Entities.Customer> GetData(Filter filter) { 
    var customers = from c in db.Customers 
        select new Entites.Customer { 
        ID = c.ID, 
        FullName = c.Name, 
        Country = c.Country 
        }; 

    return = filter.Apply(customers).ToList(); 
} 

“应用”是需要条件的集合,并且使用动态LINQ Libary适用所有的人的方法。

方法的GetData被称为像这样:

private void DemoCallGetDataMethod() { 
    var filter = new Filter(); 
    filter.AddCondition("Country", "Austria"); 

    var list = myCustomerDAL.GetData(filter); 
    // do something 
} 

SQL Server获取一个选择statment:

SELECT [t0].ID, [t0].Name, [t0].Country 
    FROM Customer [t0] 
WHERE [t0].Country = @p0 

(@ P0是它的值设置为 “奥” 的参数)。

如果我只想过滤“顶级”(主)级别的值,一切都很好。但是,由于我在筛选器表单上的用户输入上构建了筛选器,因此有些情况下用户希望按详细级别的值进行筛选(即只有在用户单击“搜索”后才知道要筛选的列)。

我无法找到一个解决方案:“让所有来自奥地利的客户,谁买百事可乐”。

我已经尝试了几件事情,其中​​没有一件似乎工作。其基本思想是:
1. Add support for CONTAINS到DynamicLibrary
2.更改我的代码

public override List<Entities.Customer> GetData(Filter filter) { 
    var customers = from c in db.Customers 
        select new Entites.Customer { 
        ID = c.ID, 
        FullName = c.Name, 
        Country = c.Country, 
        Items = c.Order.SelectMany(o => o.Item).Select(i => i.ItemId).ToList() 
        }; 

    return = filter.Apply(customers).ToList(); 
} 

private void DemoCallGetDataMethod() { 
    var filter = new Filter(); 
    filter.AddCondition("Country","=", "Austria"); 
    filter.AddCondition("Items","Contains", "11"); // 11 = Id for Pepsi 

    var list = myCustomerDAL.GetData(filter); 

    // do something 
} 

抛出的exepction是:在没有通用方法 '包含':

System.InvalidOperationException类型'System.Linq.Enumerable'与提供的类型参数和参数兼容。如果方法是非泛型的,则不应提供类型参数。

没有人有任何知道我做错了吗?或者我只是走错了方向,我应该尝试一些其他的方法?哪一个? :)

编辑:改变了我的例子

+0

对不起荫不知道你是什么后,你提到的文章还给出了一个答案给你同样的问题面对避免这种例外。因为你想遵循这条路线,我真的不明白你在做什么:)? – user182630

+0

filter.AddCondition( “项目”, “含有”, “百事可乐”); - 这仅适用于和字符串作品,而不是列出和字符串 – Tsabo

+0

@ user182630我希望能够从子查询一般由值过滤,不仅为特定的情况下。那篇文章的方法只适用,如果你硬编码您的过滤器,这不是我能做的事。 –

回答

2

@ user182630我希望能够从子查询中 的值来过滤一般情况下,不仅对一个具体案例。那篇文章 这种方法只适用,如果你硬编码您的过滤器,这是不是一个东西,我可以做 。 - 马尔科Juvančič9分钟前

有一个读通过这篇文章http://csharpindepth.com/articles/chapter5/closures.aspx

2

我用PredicateBuilder在我的应用程序的动态查询。

Predicate Builder

在你的情况下,我想这会是这样的:

string MyCountry = "Austria"; 
string MyProductId = 11 

var Predicate = PredicateBuilder.True<db.Customers>(); 
Predicate = Predicate.And(p=>p.Country ==MyCountry && p.Order.SelectMany(o=>o.Item).Where(i=>i.id == 11).Count() >0); 

var list = Customers.Where(Predicate).Select(s=>s).ToList(); 
+0

这种方法失败了,“只有在用户点击搜索之后才知道要过滤的列”要求。 –

+0

那么如果所有列提前知道,那么这是没有问题的。 – Tsabo

+0

他们不是。方法“应用”过滤器不知道任何有关列。 –