Passing a parameter to a linq predicate

别来无恙 提交于 2019-12-07 17:10:53

问题


I want to write code like the following -

    public IQueryable<Invoice> InvoiceFilterForMonthAndYear(DateTime? monthAndYear = null)
    {
        var invoices = _invoices.Where(MonthAndYearPredicate(monthAndYear);
        return invoices;
    }

    private bool MonthAndYearPredicate(Invoice invoice, DateTime? monthAndYear)
    {
        //code to check if the invoice start or end dates is from the falls in the month I am checking for
    }

But I can't use a predicate like that because the predicate expects just one parameter.

I know I could write a Where clause in InvoiceFilterForMonthAndYear to do the work, but I want to put the logic for the comparison into its own method.


回答1:


It works if your method for comparison returns an expression:

private Expression<Func<Invoice,bool>> MonthAndYearPredicate(
    DateTime? monthAndYear)
{
    return i => i.StartDate >= monthAndYear; // or whatever
}

To be called like in your example:

var invoices = _invoices.Where(MonthAndYearPredicate(monthAndYear));

Or you could extract the logic into an extension method of IQueryable<Invoice>:

public static class QueryExtensions
{
    public static IQueryable<Invoice> WhereMonthAndYear(
        this IQueryable<Invoice> query, DateTime? monthAndYear)
    {
        return query.Where(i => i.StartDate >= monthAndYear); // or whatever
    }
}

To be called like so:

var invoices = _invoices.WhereMonthAndYear(monthAndYear);

Keep in mind that in both cases you have to use valid LINQ-to-Entities expressions that EF can translate into SQL. It only makes the expressions reusable for different queries but does not extend its capabilities.




回答2:


You won't be able to extract the logic out into a method. If you do, then the expression tree that results from the method call won't have enough information for the query provider to generate the query. You need to inline the logic so that it all ends up in the expression tree.



来源:https://stackoverflow.com/questions/18967416/passing-a-parameter-to-a-linq-predicate

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!