Entity Framework 4 和 Linq:OrderBy 嵌套在查询中的字段:重构我的代码

发布于 2024-10-04 04:55:27 字数 1777 浏览 0 评论 0原文

首先,Thomas Levesque有一个很好的解决方案对于相关表中的排序字段,其中关系可能并不总是存在:

userQuery = userQuery.OrderBy(u => 
    (u.Department != null) ? u.Department.Name : String.Empty);

我需要做同样的事情。我的聚合根是巨大的:

myQuery = myQuery.OrderBy(p =>
  (p.Seconds == null
    ? 0
    : p.Seconds.FirstOrDefault() == null
      ? 0
      : p.Seconds.First().Thirds == null
        ? 0
        : p.Seconds.First().Thirds.FirstOrDefault() == null
          ? 0
          : p.Seconds.First().Thirds.First().Forths == null
            ? 0
            : p.Seconds.First().Thirds.First().Forths.FirstOrDefault() == null
              ? 0
              : p.Seconds.First().Thirds.First().Forths.First().myField));

这真的是这样做的方法吗,还是有更容易阅读的东西?我的另一个问题是嵌套的 myField 在顶级查询中有一个匹配的“默认”值,也由 myField 命名。这个想法是通过这两个字段的合并来排序(??)。

编辑:我认为这将包括第一个字段中的“默认值”:

myQuery = myQuery.OrderBy(p =>
  (p.Seconds == null
    ? p.myDefaultField // Used to be zero
    : p.Seconds.FirstOrDefault() == null
      ? p.myDefaultField
      : p.Seconds.First().Thirds == null
        ? p.myDefaultField
        : p.Seconds.First().Thirds.FirstOrDefault() == null
          ? p.myDefaultField
          : p.Seconds.First().Thirds.First().Forths == null
            ? p.myDefaultField
            : p.Seconds.First().Thirds.First().Forths.FirstOrDefault() == null
              ? p.myDefaultField
              : p.Seconds.First().Thirds.First().Forths.First().myField));

如何重写此 OrderBy 使其更清晰? 此代码失败,并出现错误“无法比较类型为 'System. Collections.Generic.IEnumerable`1'。仅支持原始类型(例如 Int32、String 和 Guid)和实体类型。”

First, Thomas Levesque had a good solution for ordering fields in a related table where the relation may not always be there:

userQuery = userQuery.OrderBy(u => 
    (u.Department != null) ? u.Department.Name : String.Empty);

I need to do the same thing. My aggregate root is enormous:

myQuery = myQuery.OrderBy(p =>
  (p.Seconds == null
    ? 0
    : p.Seconds.FirstOrDefault() == null
      ? 0
      : p.Seconds.First().Thirds == null
        ? 0
        : p.Seconds.First().Thirds.FirstOrDefault() == null
          ? 0
          : p.Seconds.First().Thirds.First().Forths == null
            ? 0
            : p.Seconds.First().Thirds.First().Forths.FirstOrDefault() == null
              ? 0
              : p.Seconds.First().Thirds.First().Forths.First().myField));

Is this really the way to do this, or is there something much easier to read? My other problem is that the nested myField has a matching "default" value sitting in the top level Query, also named by myField. The idea was to Order by the coalesce of these two fields (??).

Edit: I think this would include the "default value" from the first field:

myQuery = myQuery.OrderBy(p =>
  (p.Seconds == null
    ? p.myDefaultField // Used to be zero
    : p.Seconds.FirstOrDefault() == null
      ? p.myDefaultField
      : p.Seconds.First().Thirds == null
        ? p.myDefaultField
        : p.Seconds.First().Thirds.FirstOrDefault() == null
          ? p.myDefaultField
          : p.Seconds.First().Thirds.First().Forths == null
            ? p.myDefaultField
            : p.Seconds.First().Thirds.First().Forths.FirstOrDefault() == null
              ? p.myDefaultField
              : p.Seconds.First().Thirds.First().Forths.First().myField));

How could I rewrite this OrderBy to be cleaner? This code fails with an error of "Cannot compare elements of type 'System.Collections.Generic.IEnumerable`1'. Only primitive types (such as Int32, String, and Guid) and entity types are supported."

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

逆蝶 2024-10-11 04:55:27

我认为你这里有一种非常令人讨厌的代码味道,但是使用你所拥有的东西我不会在这样的 LINQ 查询中处理这个问题。只是为了可读性,我会

myQuery = myQuery.OrderBy(p =>
  (p.HasValidFields()
    ? p.Seconds.First().Thirds.First().Forths.First().myField
    : p.myDefaultField
  ));

在 p 的班级中做类似的事情

private bool HasValidFields
{
  get
  {
    return p.Seconds != null &&
           p.Seconds.FirstOrDefault() != null &&
           .... ;
  }
}

I think you have a pretty nasty code smell going on here, but working with what you have got I wouldn't handle this in a LINQ query like that. Just for the sake of readability I'd do something like

myQuery = myQuery.OrderBy(p =>
  (p.HasValidFields()
    ? p.Seconds.First().Thirds.First().Forths.First().myField
    : p.myDefaultField
  ));

And inside of p's class

private bool HasValidFields
{
  get
  {
    return p.Seconds != null &&
           p.Seconds.FirstOrDefault() != null &&
           .... ;
  }
}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文