将两个不同的PredicateBuilders与表达式结合使用

时间:2014-09-25 15:26:24

标签: c# linq linq-expressions predicatebuilder linq-extensions

我有一个谓词构建器,它工作正常

 var filter = sortKeys.Aggregate(filter, (currentFilter, sortkey) => currentFilter.Or(
                            x => x.Appointments.Any(y => y.RowStatus == Constants.CurrentRowStatus )));

我现在正在尝试将约会中的条件拆分为另一个谓词构建器,以便我可以随时添加条件并重用该函数。

我曾尝试创建一个表达式,然后在主谓词构建器中使用它,但它失败了

private static Expression<Func<Appointment, bool>> TmpApt(string status)
    {
        var predicate = PredicateBuilder.False<Appointment>();

        predicate = predicate.Or(p => p.RowStatus == status);

        return predicate;
    }

更改主谓词以使用上面的表达式

var filter = sortKeys.Aggregate(PredicateBuilder.True<Person>(), (current, s) =>
                                current.Or(x => x.Appointments.Any(TmpApt(s))));

显示错误

  

参数类型&#39; System.Linq.Expressions.Expression<System.Func<Appointment,bool>>&#39;是       不能分配给参数类型System.Func<Appointment,bool>

我甚至尝试了像Expand这样的LinqKit扩展方法,但可以找到解决方案。

还尝试了Reusable predicate expressions in LINQ,然后在编译时没有显示任何错误,但在应用程序端显示时,它显示

  

用于查询运算符的不支持的重载&#39; Any&#39;。

任何人都可以帮我解决错误或建议替代解决方案。

1 个答案:

答案 0 :(得分:1)

您可以使用LINQKit调用您想要使用它的位置的表达式:

var predicate = TmpApt();
var filter = sortKeys.Aggregate(PredicateBuilder.False<Person>(),
    (current, s) => current.Or(x =>
        x.Appointments.Any(appointment => predicate.Invoke(appointment))))
        .Expand();

请注意,由于其实现中存在错误,您需要将TmpApt拉出到LINQKit的变量中以成功评估它。

另请注意,您需要将汇总操作初始化为False,因为True与任何内容进行了对比true

另请注意,您可以将TmpApt的实施简化为以下内容:

private static Expression<Func<Appointment, bool>> TmpApt()
{
    return p => p.RowStatus == Constants.CurrentRowStatus;
}

此处不需要使用谓词构建器Or False