按字段对列表进行排序(C#)

44

我有这样一个类:

class SortNode
{
    public Int32 m_valRating = 0;

    public SortNode(Int32 valRating)
    {
        this.m_valRating = valRating;
    }
}

还有一个列表 refSortNodeList:

List<SortNode> refSortNodeList = new List<SortNode>();

Random refRandom = new Random();

for (int i = 0; i < 100; ++i)
{
    refSortNodeList.Add(new SortNode(refRandom.Next(-10, 30)));
}

foreach (var varSortNode in refSortNodeList)
{
    Console.WriteLine("SortNode rating is {0}", varSortNode.m_valRating);
}

如何方便地按照 m_valRating 字段对我的 refSortNodeList 进行排序?或者我需要使用其他的 List 类?


2
公共字段不是一个好主意,顺便说一下。 - Marc Gravell
8个回答

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

2
如果进行比较的对象为空,则会抛出异常。 - Jon Hanna
3
@Jon - 当然你可以编写代码来解决这个问题,但是在这里一个空值可能会导致错误。 - Marc Gravell
我刚刚遇到了足够多的与空值比较排序错误,让我对它们双倍警惕,但它们不应该发生在这里,你是正确的。 - Jon Hanna

20

原地修改:

refSortNodeList.Sort(
  (x, y) =>
    x == null ? (y == null ? 0 : -1)
      : (y == null ? 1 : x.m_valRating.CompareTo(y.m_valRating))
);

创建一个新的枚举:

var newEnum = refSortNodeList.OrderBy(x => x.m_valRating);

创建新列表:

var newList = refSortNodeList.OrderBy(x => x.m_valRating).ToList();

原地排序(in-place)是最快和最节约内存的,但如果您还想保留旧列表,则不适用。

下一种方法比上一种方法更快,并且在处理时就能得到结果,但您必须重新排序才能再次使用它,在这种情况下,最好选择第三种方法。


15

使用Linq的order by语句。

var mySortedList = refSortNodeList.OrderBy(x => x.m_valRating);

这里有一个真实的示例,我正在从数据库中获取一个列表,但概念完全相同。

 vendorProducts = (from vp in db.COMPANIES_VND_PRODUCTS
                    join p in db.CT_CT_INV_CLASSES on vp.CLASS_ID equals p.CLASS_ID
                    join m in db.CT_CT_MODALITY_CODES on vp.MODALITY_ID equals m.MODALITY_ID
                    where vp.COMPANY_ID == companyId
                    select new ProductTypeModality
                    {
                      Active = p.ACTIVE.Equals("Y") ? true : false,
                      BioMedImaging = p.BIOMED_IMAGING,
                      Code = p.CLASS_CODE,
                      Description = p.DESCRIPTION,
                      Id = p.CLASS_ID,
                      PricingMargin = p.PRICING_MARGIN,
                      ModalityCode = m.MODALITY_CODE,
                      ModalityId = m.MODALITY_ID,
                      VendorId = companyId
                    }).OrderBy(x => x.Code).ToList<ProductTypeModality>();

2
您可以使用Linq进行基本排序:
refSortNodeList.OrderBy(n => n.m_valRating);

如果您需要更复杂的排序,您需要实现 IComparable 接口以使用内置的排序功能。

2

1

试试这个:

refSortNodeList.Sort(new delgate(SortNode x, SortNode y)
   {
       return x.CompareTo(y);
    }
);

0

使用linq很容易:

var newlist = refSortNodeList.sort( n => n.m_valRating );

Sort() 不返回值,而 OrderBy() 也不返回列表。 - mgronber
OrderBy返回一个IOrderedEnumerable<T> (http://msdn.microsoft.com/en-us/library/bb534966.aspx)。 - dcarneiro

0
List<SortNode> refSortNodeList = new List<SortNode> ();

Random refRandom = new Random ();

for (int i = 0; i < 100; ++i) {
    refSortNodeList.Add (new SortNode (refRandom.Next (-10, 30)));
}

// Use this (Linq) if you're using .NET 3.5 or above.
var sortedList = refSortNodeList.OrderBy (node => node.m_valRating);
foreach (var varSortNode in sortedList) {
    Console.WriteLine ("SortNode rating is {0}", varSortNode.m_valRating);
}

// Use this otherwise (e.g. .NET 2.0)
refSortNodeList.Sort (
    delegate (SortNode n1, SortNode n2) {
        return n1.m_valRating.CompareTo (n2.m_valRating);
    }
);

foreach (var varSortNode in refSortNodeList) {
    Console.WriteLine ("SortNode rating is {0}", varSortNode.m_valRating);
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接