C# List<T> 任意の項目を削除・抽出・変換する

独自に定義したクラスを格納した List<T> で任意の項目を削除・抽出・変換する方法について説明しています。

.NET Framework 3.0 以降ではラムダ式を使用してシンプルに記載することができるようになりましたので、ここではラムダ式を使用して、独自クラスの List<T> に対して任意の項目を削除・抽出・変換してみます。

まずは、独自に定義したクラスですが、ここでは単純に ID と Name をプロパティに持つクラスを使用します。

    public class Employee
    {
        public int ID { getset; }
        public string Name { getset; }
    }

適当なデータを作成して、それぞれ削除・抽出・変換を行っていますが、すべて1行で書く事ができます。

        // ~ 適当なデータをList<T>と配列に格納する ~ 
        List<Employee> list = new List<Employee>();
        list.Add(new Employee(2, "William Henry Gates"));
        list.Add(new Employee(3, "Steven Paul Jobs"));
        list.Add(new Employee(1, "Lawrence Edward Larry Page"));
        
        // リストをID順でソートする
        list.Sort((a, b) => a.ID - b.ID);
         
        // 結果、下記の順にソートされます
        // ID=1 Name=Lawrence Edward Larry Page
        // ID=2 Name=William Henry Gates
        // ID=3 Name=Steven Paul Jobs
         
        // List<string>に変換する
        List<string> s = list.ConvertAll(x => string.Format("ID={0} Name={1}", x.ID, x.Name));
         
        // 結果、下記のList<string>に変換されます
        // "ID=1 Name=Lawrence Edward Larry Page"
        // "ID=2 Name=William Henry Gates"
        // "ID=3 Name=Steven Paul Jobs"
         
        // IDが奇数の項目を抽出する
        List<Employee> oddList = list.FindAll(x => x.ID % 2 != 0);
         
        // 結果、下記の項目が抽出されます
        // ID=3 Name=Steven Paul Jobs
        // ID=1 Name=Lawrence Edward Larry Page
         
        // 名前の長さが20文字未満の項目を削除する
        list.RemoveAll(x => x.Name.Length < 20);
         
        // 結果、下記の項目が削除されます
        // ID=2 Name=William Henry Gates
        // ID=3 Name=Steven Paul Jobs

ラムダ式の部分が良く分からない方の為に、ラムダ式を使わない書き方も紹介します。まず、それぞれ変換や抽出を行うメソッドを用意します。それぞれの引数や戻り値はMSDNを参照してください。

        /// <summary>
        /// 文字列に変換
        /// </summary>
        static string ConvertToString(Employee x)
        {
            return string.Format("ID={0} Name={1}", x.ID, x.Name);
        }
         
        /// <summary>
        /// IDが奇数?
        /// </summary>
        static bool IsOddID(Employee x)
        {
            return x.ID % 2 != 0;
        }
        
        /// <summary>
        ///  名前の長さが20文字未満?
        /// </summary>
        static bool IsShortName(Employee x)
        {
            return x.Name.Length < 20;
        }

ConvertAll(), FindAll(), RemoveAll(), の引数にそれぞれ上で定義したメソッドを指定します。

        // List<string>に変換する
        List<string> stringList = employeeList.ConvertAll(ConvertToString);
         
        // IDが奇数の項目を抽出する
        List<Employee> oddList = employeeList.FindAll(IsOddID);
         
        // 名前の長さが20文字未満の項目を削除する
        employeeList.RemoveAll(IsShortName);

ラムダ式の部分はこれらと全く等価のコードになります。ソースコード中に何度も同じ比較を行う場合はメソッドを用意し、1度しか使用されない場合はラムダ式を使って簡潔に記載するのが良いと思われます。

参考:独自クラスの配列や List<T> を任意にソートする
使用環境: Visual Studio 2010 .NET Framework 3.0 以降

C# メニューリスト