2012-03-21 7 views
1

私はアドレス帳プログラムを作成しています。私は各人の詳細をList<Person>に保存しています。私はこのリストを姓(名前が同じ場合は名前を使用)または郵便番号で並べ替えることができる必要があります。指定されたプロパティを使用してオブジェクトの一般的なリストをアルファベット順に並べ替えます。

は、これまでのところ私はこれを持っている:

public class Person 
{ 
    public string LastName { get; set; } 
    public string FirstName { get; set; } 
    public string PostCode { get; set; } 
    // etc.. 
} 

public class AddressBook 
{ 
    public List<Person> People { get; set; } 

    // asc: ascending or descending 
    // column: the property to use when sorting 
    //   (in my case either LastName or Postcode) 
    public void Sort(bool asc, string column) 
    { 
     // What should I put here? 
    } 

    // etc... 
} 

私はICompareIComparableインターフェースを使用して試してみましたが、私はちょうどそれを取得しておりません。

Sortの方法はどのように記述しますか?

+0

C#/ .NETのどのバージョンを使用していますか? –

+0

4.0だと思います..... – Jammerz858

+0

あなたの質問をきれいにして読みやすくしました。私はそれが大丈夫だと思います。 –

答えて

3

あなたはIComparer<T>の実装を使用することができます。

public class PersonComparer : IComparer<Person> 
{ 
    private readonly bool _sortAscending; 
    private readonly string _columnToSortOn; 

    public PersonComparer(bool sortAscending, string columnToSortOn) 
    { 
     _sortAscending = sortAscending; 
     _columnToSortOn = columnToSortOn; 
    } 

    public int Compare(Person x, Person y) 
    { 
     if(x == null && y == null) return 0; 
     if(x == null) return ApplySortDirection(-1); 
     if(y == null) return ApplySortDirection(1); 

     switch(_columnToSortOn) 
     { 
      case "LastName": 
       return ApplySortDirection(SortByName(x, y)); 
       break; 
      case "PostCode": 
       return ApplySortDirection(SortByPostCode(x, y)); 
       break; 
      default: 
       throw new ArgumentOutOfRangeException(
        string.Format("Can't sort on column {0}", 
        _columnToSortOn)); 
     } 
    } 

    private int SortByPostCode(Person x, Person y) 
    { 
     return x.PostCode.CompareTo(y.PostCode); 
    } 

    private int SortByName(Person x, Person y) 
    { 
     var lastNameResult = x.LastName.CompareTo(y.LastName); 
     if(lastNameResult != 0) 
      return lastNameResult; 
     return x.FirstName.CompareTo(y.FirstName); 
    } 

    private int ApplySortDirection(int result) 
    { 
     return _sortAscending ? result : (result * -1); 
    } 
} 

あなたのAddressBookSort方法でそれを使用しますこのようなクラス、PeopleList<Person>です:

public void Sort(bool asc, string column) 
{ 
    People.Sort(new PersonComparer(asc, column)); 
} 

このコードは、インプレースの並べ替えを使用することの利点を持っています。

+0

Brill!ダニエルありがとう。 – Jammerz858

+0

完全に動作します。そして...(さらに良い)私はそれを理解する...ありがとう! – Jammerz858

+0

@ user1243505:どうぞよろしくお願いいたします。私の答えを受け入れることを忘れないでください:[回答を受け入れる方法](http://meta.stackexchange.com/questions/5234/how-does-accepting-an-answer-work) –

4

あなたはLINQの拡張メソッドを使用して試すことができますOrderByOrderByDescendingThenByThenByDescending

using System.Linq; 

// ... 

public void Sort(bool asc, string column) 
{ 
    switch (column) 
    { 
     case "LastName": 
      People = People.OrderBy(x => x.LastName).ThenBy(x => x.FirstName).ToList(); 
      break; 
     case "PostCode": 
      People = People.OrderBy(x => x.PostCode).ToList(); 
      break; 
     default: 
      // error handling 
    } 

    if (!asc) 
    { 
     People.Reverse(); 
    } 
} 

ます。また、このコードを簡素化することになるの動的LINQで見ることができます。

+0

ご返信ありがとうございます。私が下で述べたように、リストをソートするコードを取得する方法を理解していないので、linqをもっと調べる必要があります。しかし、あなたの助けをありがとう。 – Jammerz858

+0

@ user1243505:もし私があなただったら、私の将来に投資してLINQを学ぶでしょう。それははるかに簡単で使いやすくなっています。あなた自身の教育へのわずかな投資は、長期的には多くの時間を節約し、将来的には貴重なプログラマーになるでしょう。しかし、それはあなたの人生、あなたのキャリア、あなたの選択です... –

1

と仮定:LINQのと、その後

List<Person> personList; 

を:

IEnumerable<Person> orderedByLastName = personList.OrderBy(p => p.LastName) 
+0

これは私のために働いていないので、スペンダー、私は明らかに何かが(linqに少し読書を行う必要があります)が不足しています。私がソートメソッドを通してテストを実行するとき、Listはとにかくソートされません。 – Jammerz858

+0

@ user1243505:これは - Markの答えも - インプレースソートを行わないからです。ソートされた順序で元のリストの内容を含む* new *オブジェクトを返します。 –

関連する問題