2012-04-07 6 views
0

私は代議員と一緒に遊んでいて、何が起こっているのかわからない状況に遭遇しました。参照として渡されている間の代議員の振る舞い

私のロジックでは、 "greetings"デリゲートの呼び出しリストは2を返すべきですが、ただ1を返します。ご覧のとおり、私が作成したオブジェクトにデリゲート参照を渡しています。私はデリゲートが外部からプライベートメソッドを参照できることを確認したかっただけで、メソッドがデリゲートへのメソッドの割り当て中にアクセス可能であることが唯一の要件です。

class Program 
    { 
     static void Main(string[] args) 
     { 
      Action greetings = FirstGreeting; 

      Test test = new Test(); 
      test.AddGreeting(greetings); 

      Console.WriteLine(greetings.GetInvocationList().Count()); 

      greetings(); 

      Console.ReadLine(); 
     } 

     static void FirstGreeting() 
     { 
      Console.WriteLine("This is the first greeting."); 
     } 
    } 

    class Test 
    { 
     public void AddGreeting(Action greetings) 
     { 
      greetings += new Action(SecondGreeting); 
     } 

     private void SecondGreeting() 
     { 
      Console.WriteLine("This is the second greeting."); 
     } 
    } 

答えて

3

あなたが見ることができるように、私は私が作成したオブジェクトへのデリゲートの参照を渡しています。

はい、いますが、その後、使用している:

greetings += new Action(SecondGreeting); 

これは新しいデリゲートを作成する - それが既存デリゲートを変更しません。代理人は文字列のように不変です。

public void AddGreeting(ref Action greetings) 
{ 
    greetings += new Action(SecondGreeting); 
} 

をして

test.AddGreeting(ref greetings); 

(または新しいデリゲートへの参照を返すようにそれを呼び出す:あなたは本当にコードは、あなたが期待されるだろうように動作するようにしたい場合は、使用する必要があるだろう、Peterの答えにあるように)

+=の詳細については、article on delegates and eventsを参照してください。

+0

ありがとうございました。 –

1

私はちょうどあなたのコードを試して、あなたが意味するものを見ることができます。 AddGreeting()メソッドにその行に呼び出しリストを出力する行を追加すると、そこに2つのメソッドが表示されます。しかし、Jon Skeetが指摘したように、代理人は不変であり、作成した新しい(マルチキャスト)代理人は返されていません。

私はあなたがこれにあなたの方法を変更する提案:これは今、あなたの呼び出しの正しいセットを与えるよう

public Action AddGreeting(Action greetings) 
{ 
    return greetings + new Action(SecondGreeting); 
} 

+0

うん、それは参照渡しの代わりです。 –

関連する問題