過去に実務でC++を触っていたときにクラスをnewでインスタンス化→要らなくなったらdeleteで削除というのを徹底していた。
で、最近Unity学習で触っているC#ではそういえばdeleteなんて書いたことねぇ・・・とふと思った。
※調べてみると、C#でのクラスインスタンスはclassの変数にnullをセットすると
C#のガベージコレクションという機能がもう使われてないと判断して削除してくれるらしい。
C++、C#のクラスにおけるインスタンス化、利用、削除の流れを書いたコードは以下。
やっぱり色々なんか使い方違う・・・
// クラスをインスタンス化し、クラスのポインタ型変数にインスタンスのポインタを格納
ClassA* classA = new ClassA();
// int型のmember_aをコンソールへ出力
printf("%d¥n", classA->member_a);
// インスタンスを削除
delete classA;
// クラスをインスタンス化し、クラスの変数(あれ、ポインタじゃない?)に格納
ClassA classA = new ClassA();
// int型のmember_aをUnityのコンソールへ出力
Debug.Log(classA.member_a);
// インスタンスを削除
classA = null;
一番の違和感は、C++ではクラスをnewするとそのインスタンスのポインタが返ってきて、それをクラスのポインタ型変数に代入して、アロー演算子とかいうやつでアクセスする、という形なのに、C#ではポインタとか使った記憶がない。ちょっとまって。C#ではnewしたときに何が返ってくるの・・・?
そもそもC#ではポインタを使うことが非推奨であるらしい(重大なバグにつながるかららしい。のっぴきならない事情があれば無理やり使うこともできるみたいだが)。・・・ということはそもそもnewしてもポインタなんかかえってきてるわけなさそう。
じゃあなにが返ってくるのか。それは・・・newした対象のデータ型によるらしく。C#の世界では、データの型に応じて、値型もしくは参照型に区分され、扱われるらしい。それはそのデータ型の変数を宣言したときも同等。
newしたときに値型で返ってくる | newしたときに参照型で返ってくる |
---|---|
- 構造体 - 列挙型 |
- string - object - 配列 - クラス - インターフェース - デリゲート |
クラスは参照型という扱いになるんですね。