今回はC#のプログラムを書いているとたまに使うことがあるrefキーワードについて、使い方を解説します。
refキーワードの基本
refキーワードは参照渡しでオブジェクトを渡すためのキーワードです。と言っても良く意味が分からないと思うので使い方を見ていきましょう。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 |
static void Main(string[] args) { int a = 1; Console.WriteLine(a);// "1"が表示される Test1(a); Console.WriteLine(a);// "1"が表示される int b = 1; Console.WriteLine(b);// "1"が表示される Test2(ref b); Console.WriteLine(b);// "2"が表示される } static void Test1(int a) { a = 2; } static void Test2(ref int b) { b = 2; } |
refキーワードを付けない場合、メソッド内で引数で渡されてきたデータを更新しても、呼び出し元のデータは変化しません。
それに対し、refキーワードを付ける場合、メソッド内で引数のデータを更新すると、呼び出し元のデータも変化します。
このようにrefキーワードを付けることでint、double等の値型の引数でも参照型引数として扱うことができます。
refキーワードはどんな時に使うと役に立つのか
refキーワードは普段プログラムを書いていて使うことはあまりありません。使わなくてもプログラム書けるには書けますからね。。
でもプログラマーの私が使う場面をあげるなら、戻り値が必要なメソッドで引数のデータも更新したい場合です。↓
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
static void Main(string[] args) { int a = 1; Console.WriteLine(a);// 1と表示される TryUpdate(true, ref a); Console.WriteLine(a);// 2と表示される } static bool TryUpdate(bool flag, ref int a) { if (flag) { a = 2; return true; } return false; } |
このプログラムの場合、TryUpdateメソッドではの戻り値でフラグを返していて第1引数のflagがtrueの場合のみ値更新しています。
このように戻り値が使えないが、引数を経由して呼び出し元⇔呼び出し先でデータの受け渡しを行いたい場合refキーワードが役に立ちます。
参照型にrefキーワードを付ける意味
intやdouble等の値型のデータに対しrefキーワードを付けることで、参照型データとしてメソッドへ渡せるようになることは理解できたと思います。
でもここで1つ疑問が浮かびます。class等の参照型のデータに対してrefキーワードを付けたらどうなるのでしょうか?
挙動が変わらないのではと思う方が多いと思いますが、refキーワードの有り無しで動きは変わります。次のコードを見てください。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 |
public class TestCalss { public int A; } static void Main(string[] args) { TestCalss test1 = new TestCalss(); Update1(test1); Console.WriteLine(test1.A); // 1が表示される TestCalss test2 = new TestCalss(); Update2(ref test2); Console.WriteLine(test2.A); // 2が表示される } static void Update1(TestCalss test) { test.A = 1; test = new TestCalss(); test.A = 2; } static void Update2(ref TestCalss test) { test.A = 1; test = new TestCalss(); test.A = 2; } |
Update1のメソッドではrefキーワード無しで、Update2のメソッドではrefキーワードを付けて引数のTestClassを渡しています。
出力結果に違いが出ているのが分かると思います。
refキーワードを付けない場合だと呼び出し元のオブジェクト自体の更新(newで新規オブジェクトを割り当て)はできませんが、refキーワードを付ければ呼び出し元のオブジェクト更新も行うことが可能です。
まとめ
今回はC#のrefキーワードについて解説しました。正直プログラムを書いていてもあまり使う機会は多くありませんが、覚えておくとプログラムを作る際や人のコードを読む際に役に立ちます。知らなかった人はぜひ覚えてくださいね。