【问题标题】:Sort a list by column name string按列名字符串对列表进行排序
【发布时间】:2014-04-15 23:43:56
【问题描述】:

假设我有这样的课程

public class model
{
    public int id{get;set;}
    public string name{get;set;}
    public string department{get;set;}
}

我有一个模型类型列表

List<model> modelList = List<model>();

如何按列名和排序方向对模型列表进行排序?

我尝试过的方法:

public List<model> sortModelList(string columnName, SortDirection direction)
{
   //Method 1:
   //The below code was unable to sort by column and unable to set the sort direction
   return modelList.Sort();

   //Method 2:
   //The below code was unable to sort by the columnName parameter and unable to set the sort direction
   return modelList.OrderBy(a=>a.name)

  //What I can do in order to sort the list by "columnName" parameter and set the sort direction? (Ascending / Descending)
}

【问题讨论】:

标签: c# list sorting


【解决方案1】:

如果您需要将列名作为参数传递,那么您需要使用反射来进行比较。您可以执行以下操作:

modelList.OrderBy(a => a.GetType().GetProperty(columnName).GetValue(a, null));

当然,您必须进行适当的空值检查等,我假设您能够处理好这些。

【讨论】:

  • 谢谢,这正是我想要的:)
  • LINQ to Entities does not recognize the method 'System.Object GetValue(System.Object, System.Object[])' method, and this method cannot be translated into a store expression 让您知道这完全消除了使用 iqueryable 的意义。
【解决方案2】:

我想你正在寻找the overload of Sort() that takes a comparison function

例如:

modelList.Sort((m1, m2) => string.Compare(m1.name, m2.name));
// descending
modelList.Sort((m1, m2) => -string.Compare(m1.name, m2.name));

OrderBy 具有类似的灵活性,但返回一个已排序的新序列,而不是修改原始列表。所以,你可以这样做:

var newList = modelList.OrderBy(m => m.name).ToList();
// descending
var newList = modelList.OrderByDescending(m => m.name).ToList();

要指定要动态排序的属性,请考虑以下代码:

public void SortList<T>(List<T> list, string columnName, SortDirection direction)
{
    var property = typeof(T).GetProperty(columnName);
    var multiplier = direction == SortDirection.Descending ? -1 : 1;
    list.Sort((t1, t2) => {
        var col1 = property.GetValue(t1);
        var col2 = property.GetValue(t2);
        return multiplier * Comparer<object>.Default.Compare(col1, col2);
    });
}

【讨论】:

  • 但有时列表不会按名称排序,即有时可能按id排序,可能按部门排序,有什么办法可以使用此代码吗??
  • 谢谢!这很有帮助
  • 如果我想对我的List&lt;Countries&gt; countries 进行排序,我该如何使用public void public void SortList&lt;T&gt;countries = SortList(countries, "columnName", SortDirection.Ascending); 给我错误 cannot convert void to Collections.Generic.List.
  • @VDWWD 听起来您的列表类型不是List&lt;T&gt;。您可以将您的类型更改为List&lt;T&gt;,调用ToList() 执行转换,或更改SortList 以采用您正在使用的类型。最后一个选项要求您使用的类型具有排序函数,该函数采用 Comparison&lt;T&gt;IComparer&lt;T&gt;
【解决方案3】:

这样做的正确方法是编写一个客户比较函数。

您需要知道的一切都在这里:http://msdn.microsoft.com/en-us/library/w56d4y5z%28v=vs.110%29.aspx

试一试,如果还是不行就回来。

【讨论】:

    【解决方案4】:

    在这里您可以根据属性名称和排序方向创建动态表达式

    Dynamic LINQ OrderBy on IEnumerable<T>

    【讨论】:

      【解决方案5】:

      第 1 步:实现 IComparer 接口

      public class SortByName : IComparer<Customer>
      {
          public int Compare(Customer x, Customer y)
          {
              return x.Name.CompareTo(y.Name);
          }
      }
      

      第 2 步:将实现 IComparer 接口的类的实例作为参数传递给 Sort() 方法。

      SortByName sortByName = new SortByName();
      listModel.Sort(sortByName);
      

      【讨论】:

        猜你喜欢
        • 2021-06-10
        • 2020-06-22
        • 2018-07-07
        • 1970-01-01
        • 2012-04-03
        • 1970-01-01
        • 2015-03-26
        • 2018-07-02
        相关资源
        最近更新 更多