通过两个属性就地排序列表

时间:2014-02-04 13:09:54

标签: c# list class reorderlist

我有一个有两个属性的类,名称和位置。 我想按位置按此类排序列表,具有相同位置的元素应按名称排序。我正在制作静态列表,所以我想就地工作。

到目前为止,我设法通过一个属性订购列表:

list.Sort((x, y) => x.Position.CompareTo(y.Position));

此代码正常工作,我按位置排序列表,但我不知道如何实现第二部分。我发现了this个问题,但我不明白答案。

有人可以帮助我吗?

3 个答案:

答案 0 :(得分:5)

我会使用" OrderBy"和"然后":

  IEnumerable<Person> orderedPersons = persons.OrderBy(item => item.Position)
            .ThenBy(item => item.Name);

答案 1 :(得分:0)

list = list.OrderBy(item => item.Name).ToList();
list.Sort((x, y) => x.Position.CompareTo(y.Position));

答案 2 :(得分:0)

您链接的答案是正确的。按多个值排序的关键是次要属性仅在原色相等时才重要。排序比较的伪代码实现可能是:

compare x and y position
if they differ, return order
else compare name, return order

Sort方法上,如果项目相等,(x,y)=>后面的代码必须返回0,如果第一个应该在第二个之前,则返回负数,如果第二个应该在第二个之前,则必须返回正数来到第一个之前。 CompareTo方法将根据这些情况及其参数返回-1,0或1。由于您需要比较两个不同的属性,因此需要两次调用CompareTo。如果你决定将它们加在一起,你可能会遇到这样的情况:

  • x.position&lt; y.position(比较返回-1)
  • x.name&gt; y.name(比较返回1)
  • 结果0,项目被认为是相同的,您的规则 显然,在这种情况下,x应该首先出现。

要解决这个问题,我们需要确保名称比较仅在职位相等时才重要。由于CompareTo仅返回-1,0或1,如果我们将位置结果乘以2(或任何更大的数字),则名称比较将仅在位置相等时更改结果。 (因为-2 + 1 = -12 - 1 = 1

因此,使用原始链接答案中的方法,您的代码将类似于:

list.Sort((x, y) => 
    2 * x.Position.CompareTo(y.Position) 
    + x.Name.CompareTo(y.Name));