オブジェクト初期化子とコレクション初期化子 (C# プログラミング ガイド)

オブジェクト初期化子を使用すると、オブジェクトの作成時にアクセスできるフィールドまたはプロパティに、コンストラクターを呼び出して代入ステートメントを使用しなくても、値を割り当てることができます。 オブジェクト初期化子の構文では、コンストラクターの引数を指定することも、引数 (およびかっこ構文) を省略することもできます。 以下の例では、名前付きの型である Cat でオブジェクト初期化子を使用する方法と、既定のコンストラクターを呼び出す方法を示します。 Cat クラス内で自動実装プロパティが使用されています。 詳細については、「自動実装プロパティ」を参照してください。

class Cat
{
    // Auto-implemented properties.
    public int Age { get; set; }
    public string Name { get; set; }
}
Cat cat = new Cat { Age = 10, Name = "Fluffy" };

オブジェクト初期化子と匿名型

オブジェクト初期化子は、どのような場合にも使うことができますが、LINQ クエリ式で使うと特に有用です。 クエリ式では、次の宣言に示すように、オブジェクト初期化子を使うことによってのみ初期化できる匿名型が頻繁に使われます。

var pet = new { Age = 10, Name = "Fluffy" };  

匿名型を使うと、LINQ クエリ式の select 句によって元のシーケンスのオブジェクトを値と形状が元とは異なるオブジェクトに変換できます。 この方法は、シーケンス内の各オブジェクトの情報の一部のみを保存する場合に便利です。 次の例は、製品オブジェクト (p) に多くのフィールドおよびメソッドが含まれており、製品名および単価を含むオブジェクトのシーケンスを作成することにのみ関心があることを想定しています。

var productInfos =
    from p in products
    select new { p.ProductName, p.UnitPrice };

このクエリが実行されると、productInfos 変数には、次の例に示す foreach ステートメントでアクセスできるオブジェクトのシーケンスが格納されます。

foreach(var p in productInfos){...}  

作成される匿名型内の各オブジェクトには、2 つのパブリック プロパティがあります。これらのプロパティには、元のオブジェクトのプロパティまたはフィールドと同じ名前が付けられます。 匿名型を作成するときにフィールドの名前を変更することもできます。次の例では、フィールド UnitPrice の名前が Price に変更されます。

select new {p.ProductName, Price = p.UnitPrice};  

オブジェクト初期化子と Null 許容型

オブジェクト初期化子を null 許容構造体と共に使用すると、コンパイル時にエラーになります。

コレクション初期化子

コレクション初期化子を使うと、<xref:System.Collections.IEnumerable> を実装するコレクション型を初期化するときに 1 つ以上の要素の初期化子を指定でき、適切なシグネチャの Add をインスタンス メソッドまたは拡張メソッドとして使用できます。 要素の初期化子は、単純な値、式またはオブジェクト初期化子です。 コレクション初期化子を使用すると、ソース コード内でクラスの Add メソッドの呼び出しを複数回指定する必要がなくなります。コンパイラによって呼び出しが追加されるためです。

2 つの単純なコレクション初期化子を次の例に示します。

List<int> digits = new List<int> { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 };  
List<int> digits2 = new List<int> { 0 + 1, 12 % 3, MakeInt() };  

次のコレクション初期化子は、前の例で定義されている Cat クラスのオブジェクトをオブジェクト初期化子を使用して初期化します。 個々のオブジェクト初期化子は、かっこで囲まれ、コンマで区切られています。

List<Cat> cats = new List<Cat>
{
    new Cat(){ Name = "Sylvester", Age=8 },
    new Cat(){ Name = "Whiskers", Age=2 },
    new Cat(){ Name = "Sasha", Age=14 }
};

コレクションの Add メソッドで許容されている場合、コレクション初期化子の要素として null を指定できます。

List<Cat> moreCats = new List<Cat>
{
    new Cat(){ Name = "Furrytail", Age=5 },
    new Cat(){ Name = "Peaches", Age=4 },
    null
};

コレクションがインデックス作成をサポートしている場合は、インデックス付きの要素を指定することができます。

var numbers = new Dictionary<int, string> {   
    [7] = "seven",   
    [9] = "nine",   
    [13] = "thirteen"   
};  

// The following code consolidates examples from the topic.
class ObjInitializers
{
    class Cat
    {
        // Auto-implemented properties.
        public int Age { get; set; }
        public string Name { get; set; }
    }

    static void Main()
    {
        Cat cat = new Cat { Age = 10, Name = "Fluffy" };

        List<Cat> cats = new List<Cat>
        {
            new Cat(){ Name = "Sylvester", Age=8 },
            new Cat(){ Name = "Whiskers", Age=2 },
            new Cat(){ Name = "Sasha", Age=14 }
        };

        List<Cat> moreCats = new List<Cat>
        {
            new Cat(){ Name = "Furrytail", Age=5 },
            new Cat(){ Name = "Peaches", Age=4 },
            null
        };

        // Display results.
        System.Console.WriteLine(cat.Name);

        foreach (Cat c in cats)
            System.Console.WriteLine(c.Name);

        foreach (Cat c in moreCats)
            if (c != null)
                System.Console.WriteLine(c.Name);
            else
                System.Console.WriteLine("List element has null value.");
    }
    // Output:
    //Fluffy
    //Sylvester
    //Whiskers
    //Sasha
    //Furrytail
    //Peaches
    //List element has null value.
}

関連項目

C# プログラミング ガイド
LINQ クエリ式
匿名型