【问题标题】:How to use OrderBy in Linq如何在 Linq 中使用 OrderBy
【发布时间】:2016-05-05 06:03:53
【问题描述】:

我正在使用 OrderBy,但我发现我必须使用 OrderBy 作为最后一种方法,否则它将不起作用。 Distinct 运算符不保证它将保持值的原始顺序,或者如果我使用 Include,它无法对子集合进行排序。

我有什么理由不应该总是最后做 Orderby 并且不用担心订单是否保留?

编辑: 一般来说,有什么原因,比如性能影响,为什么我不应该最后使用 OrderBy。如果我使用 EnityFramework 查询数据库或仅查询某个集合,则不会。

dbContext.EntityFramework.Distinct().OrderBy(o=> o.Something); // this will give me ordered result 

dbContext.EntityFramework.OrderBy(o=> o.Something).Distinct().; // this will not, because Distinct doesnt preserve order.

假设我只想选择一个属性。

dbContext.EntityFramework.Select(o=> o.Selected).OrderBy(o=> o.Something);

如果我在选择一个属性后订购集合,订购会更快吗?所以在那种情况下,我应该最后使用 Order。我只是问是否有任何情况下不应该作为最后一个命令进行排序?

【问题讨论】:

  • 这取决于你想要做什么......
  • 请向我们展示您的代码。

标签: linq


【解决方案1】:

我有什么理由不应该总是最后做 OrderBy

可能有理由不使用OrderBy 作为最后一个语句。例如,排序属性可能不在结果中:

var result = context.Entities
                    .OrderBy(e => e.Date)
                    .Select(e => e.Name);

或者你想要一个排序的集合作为结果的一部分:

var result = context.Customers
                    .Select(c => new
                    {
                        Customer = c,
                        Orders = c.Orders.OrderBy(o => o.Date)
                        Address = c.Address
                    });

如果我在选择一个属性后订购集合,订购会更快吗?

您的示例表明您正在使用 LINQ to Entities,因此这些语句将被转换为 SQL。你会注意到...

context.Entities
       .OrderBy(e => e.Name)
       .Select(e => e.Name)

...和...

context.Entities
       .Select(e => e.Name)
       .OrderBy(s => s)

... 将产生完全相同的 SQL。所以OrderBy这两个位置没有本质区别。

我是使用实体框架查询数据库还是只查询某个集合都没有关系。

嗯,那确实很重要。例如,如果你这样做......

context.Entities
       .OrderBy(e => e.Date)
       .Select(e => e.Name)
       .Distinct()

...您会注意到 OrderBy 被 EF 完全忽略,并且名称的顺序是不可预测的。

但是,如果你这样做......

context.Entities
       .AsEnumerable() // Continue as LINQ to objects
       .OrderBy(e => e.Date)
       .Select(e => e.Name)
       .Distinct()

...您会看到排序顺序保留在不同的结果中。 LINQ to objects 显然具有与 LINQ to Entities 不同的策略。语句末尾的OrderBy 会使两个结果相等。

总而言之,根据经验,我想说的是,尽量在 LINQ 查询中尽可能晚地进行排序。这将产生最可预测的结果。

【讨论】:

    【解决方案2】:

    不知道你是不是误解了Distinct的意思。根据定义是这样的:

    通过使用默认相等比较器来比较值,从序列中返回不同的元素。

    因此,如果您有一个int 列表并且您想删除重复值,您可以使用DistinctDistinct 使用默认的相等比较器,它通过将当前元素与下一个元素进行比较来进行比较。所以,你必须先排序才能得到预期的结果。

    关于OrderBy 方法,事实上,它会进行排序。因此,如果您想在使用后对某些内容进行排序和区分:

    List<int> myNumbers = new List<int>{ 102, 2817, 82, 2, 1, 2, 1, 9, 4 };
    

    排序和删除重复数字

    // returns 1, 2, 4, 9, 82, 102, 2817
    var sortedUniques = myNumbers.OrderBy(n => n).Distinct();
    

    删除重复数字并排序

    // returns 1, 1, 2, 2, 4, 9, 82, 102, 2817
    // It occurs because the Distinct compares current number to the next one
    var sortedUniques = myNumbers.Distinct().OrderBy(n => n);
    

    只是删除重复的数字

    // returns 102, 2817, 82, 2, 1, 9, 4
    var sortedUniques = myNumbers.Distinct().OrderBy(n => n);
    

    只是排序

    // returns 1, 1, 2, 2, 4, 9, 82, 102, 2817
    var sortedUniques = myNumbers.Distinct().OrderBy(n => n);
    

    希望对你有帮助\o/

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-12-29
      • 2018-09-16
      相关资源
      最近更新 更多