【问题标题】:c# Multiple Independent Filters on Lambda Queryc# Lambda 查询上的多个独立过滤器
【发布时间】:2017-06-29 00:52:43
【问题描述】:

我今天已经为此工作了几个小时,感觉有一种简单的方法可以做到这一点,但除了蛮力之外我无法让它工作。

我的应用程序中有一个实体,用作两个对象之间的映射,基于 5 个过滤器。目标是找到与过滤器最具体匹配的记录。

现在,我手动强制执行 2^5 次查询以获取最具体的行,但感觉必须有一种更简单的方法才能做到这一点。

这里唯一的问题是数据库中可能没有匹配特定过滤器(或全部),在这种情况下我想选择 NULL 记录。

下面是我令人尴尬的蛮力查询的摘录——我首先想尝试匹配所有 5 个过滤器,然后是 4 个匹配的排列,然后是 3,然后是 2,然后是 1,最后是所有 Null。

incList.FirstOrDefault(x =>
                x.Filter1 == filter1Parameter && x.Filter2 == filter2Parameter && x.Filter3 == filter3Parameter && x.Filter4 == filter4Parameter && x.Filter5 == filter5Parameter
                || x.Filter1 == null && x.Filter2 == filter2Parameter && x.Filter3 == filter3Parameter && x.Filter4 == filter4Parameter && x.Filter5 == filter5Parameter
                || x.Filter1 == filter1Parameter && x.Filter2 == null && x.Filter3 == filter3Parameter && x.Filter4 == filter4Parameter && x.Filter5 == filter5Parameter
                || x.Filter1 == filter1Parameter && x.Filter2 == filter2Parameter && x.Filter3 == null && x.Filter4 == filter4Parameter && x.Filter5 == filter5Parameter
                || x.Filter1 == filter1Parameter && x.Filter2 == filter2Parameter && x.Filter3 == filter3Parameter && x.Filter4 == null && x.Filter5 == filter5Parameter
                || x.Filter1 == filter1Parameter && x.Filter2 == filter2Parameter && x.Filter3 == filter3Parameter && x.Filter4 == filter4Parameter && x.Filter5 == null

我原本以为我可以有一个简单的语句,如果存在则独立获取值,如果不存在则获取 null

                   incList.FirstOrDefault(x => (x.Filter1 == filter1Parameter || x.Filter1 == null) &&
                                    (x.Filter2 == filter2Parameter || x.Filter2 == null) &&
                                    (x.Filter3 == filter3Parameter || x.Filter3 == null) &&
                                    (x.Filter4 == filter4Parameter || x.Filter4 == null) &&
                                    (x.Filter5 == filter5Parameter || x.Filter5 == null));

但这没有用。

任何指针将不胜感激。

【问题讨论】:

  • 您能否详细说明“但这不起作用”?此外,使用两个或三个过滤器而不是五个过滤器会更容易阅读该示例。

标签: c# entity-framework linq lambda


【解决方案1】:

我仍在尝试全面了解要求。

但是,您是否探索过在一个单独的类中抽象这个或多个 Func。这个单独的类或类将像策略一样运行。只负责根据某个谓词过滤集合。

如果这看起来不是一个好方法,那么考虑编写自己的实现 IEqualityComparer 怎么样。这将允许您确定是什么使这些对象相等。

【讨论】:

    【解决方案2】:

    您可以引入类似“适应度函数”之类的东西,然后选择具有最大适应值的项目

    var bestMatch = incList.Select(x => new
    {
        item = x,
        fit = 
            (x.Filter1 == null 
                ? 1 
                : (x.Filter1 == filter1Parameter ? 2 : 0)) *
            (x.Filter2 == null 
                ? 1 
                : (x.Filter2 == filter2Parameter ? 2 : 0)) // and so on
    })
    .OrderByDescending(x => x.fit)
    .FirstOrDefault(x => x.fit > 0)?.item;
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2013-01-01
      • 1970-01-01
      • 2018-11-27
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多