使用CompareTo对通用列表进行排序

时间:2013-05-23 02:02:32

标签: c# list sorting generics compareto

我正在试图找出对通用通用列表进行排序的正确方法。我的数据结构的一个简单示例:

// The base class
public abstract class Item : IComparable<Item> {
    public enum Category { Hats, Shirts, ... }
    public Category category;

    public int CompareTo (Item that) {
       ...
    }
}

// One of several classes extending Item
public class Hat : Item {
    public int CompareTo (Hat that) {
       ...
    }
}

我有一个管理器类,它维护扩展Item的每个类的列表:

Dictionary<Item.Category, List<Item>> _items;

...

foreach (Item.Category category in Enum.GetValues(typeof(Item.Category))) {
    List<Item> list = _items[category];
    list.Sort();
}

我遇到的问题是,当我致电List<Item>.Sort()时,它显然没有使用特定于类的CompareTo()函数。解决这个问题的正确方法是什么?

2 个答案:

答案 0 :(得分:1)

问题是List<Item>.Sort()正在寻找你的派生类没有实现的IComparable<Item>的实现。您添加了一个CompareTo(Hat hat)方法,其 nothing 与您的IComparable<Item>实施相比,而不是它们碰巧具有相同的名称。您可以使CompareTo虚拟并重载它,但之后您必须更改覆盖的签名:

// The base class
public abstract class Item : IComparable<Item> {
    public enum Category { Hats, Shirts, ... }
    public Category category;

    public virtual int CompareTo (Item that) {
       // default implementation
    }
}

// One of several classes extending Item
public class Hat : Item {
    public override int CompareTo (Item that) {
       // override for Hats - can Hats be compared to other Items?
    }
}

非常小心你的CompareTo 对称传递,否则你的排序会失败:

对称:如果a&lt; b然后b>一个

传递:如果&lt; b和b&lt;然后a&lt; ç

我看到CompareTo的实现不具有传递性,很难诊断和修复。

您还应该花时间到override Equals and the comparison operators

答案 1 :(得分:0)

是否有理由不能只使用c#附带的内置比较?

list.OrderByDescending(..)list.OrderBy(..)

如果您想选择使用Icomparable,那么您必须告诉它要比较什么 离。

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