1. ホーム
  2. c#

foreach()は参照でイテレートするのか?

2023-08-08 05:26:25

質問

これを考えてみましょう。

List<MyClass> obj_list = get_the_list();
foreach( MyClass obj in obj_list )
{
    obj.property = 42;
}

obj はリスト内の対応するオブジェクトへの参照で、プロパティを変更したときにその変更が一度構築されたオブジェクトのインスタンスで持続するようにするためですか?

どのように解決するのですか?

はい。 obj はコレクション内の現在のオブジェクトへの参照です (仮に MyClass は実際にはクラスであると仮定しています)。もし、この参照を通じて何かプロパティを変更すれば、期待通りにオブジェクトを変更することになります。

しかし、変数 obj はイテレーション変数なので、それ自体を変更することはできません。変更しようとすると、コンパイルエラーが発生します。つまり、NULLにすることはできませんし、値型を反復している場合は、値を変更することになるので、どのメンバーも変更することはできません。

C#の言語仕様には(8.8.4)とあります。

"反復変数に対応するのは 読み取り専用のローカル変数で スコープを持つ読み出し専用のローカル変数です。 ステートメントに拡張されます。