Visual Studio に付属している C# 言語仕様を読み始めました。
C:\Program Files (x86)\Microsoft Visual Studio 11.0\VC#\Specifications\1033
章1.6.7.4 Events
では、次のことがわかりました。
イベントは、クラスまたはオブジェクトが通知を提供できるようにするメンバーです。イベントは、宣言に event キーワードが含まれていることと、型がデリゲート型である必要があることを除いて、フィールドと同様に宣言されます。
イベント メンバーを宣言するクラス内では、イベントはデリゲート型のフィールドのように動作します (イベントが抽象ではなく、アクセサーを宣言しない場合)。このフィールドには、イベントに追加されたイベント ハンドラーを表すデリゲートへの参照が格納されます。イベント ハンドルが存在しない場合、フィールドは null です。
この
List<T>
クラスは、Changed という単一のイベント メンバーを宣言します。これは、新しい項目がリストに追加されたことを示します。Changed イベントは、OnChanged 仮想メソッドによって発生します。このメソッドは、最初にイベントが null (つまり、ハンドラーが存在しないことを意味します) かどうかをチェックします。イベントを発生させるという概念は、イベントによって表されるデリゲートを呼び出すこととまったく同じです。したがって、イベントを発生させるための特別な言語構造はありません。クライアントは、イベント ハンドラを通じてイベントに反応します。イベント ハンドラーは、+= 演算子を使用して追加され、-= 演算子を使用して削除されます。次の例では、イベント ハンドラーを の Changed イベントにアタッチし
List<string>
ます。using System; class Test { static int changeCount; static void ListChanged(object sender, EventArgs e) { changeCount++; } static void Main() { List<string> names = new List<string>(); names.Changed += new EventHandler(ListChanged); names.Add("Liz"); names.Add("Martha"); names.Add("Beth"); Console.WriteLine(changeCount); // Outputs "3" } }
イベントの基になるストレージの制御が必要な高度なシナリオでは、イベント宣言で add アクセサーと remove アクセサーを明示的に指定できます。これは、プロパティの set アクセサーに多少似ています。
イベントを知ったときはかなり驚いたList.Changed
ので、Visual Studio 2012 で新しいコンソール アプリケーションを作成し、ターゲット フレームワークを .NET 4.5 に設定しました。
(Visual Studio と開発者コマンド プロンプトの両方を使用して) アプリケーションをコンパイルしようとすると、次のエラーが発生しました。
エラー CS1061: 'System.Collections.Generic.List' には 'Changed' の定義が含まれておらず、タイプ 'System.Collections.Generic.List' の最初の引数を受け入れる拡張メソッド 'Changed' が見つかりませんでした (不足していますか? using ディレクティブまたはアセンブリ参照?)
ここで何か不足していますか?ILSpy を使用してクラス定義を確認しましたが、イベントが表示されませんChanged
。