メモリ解放について、ご教授ください。
C#にて、クラスライブラリ(DLL)を作るのですが、以下のようなクラスの使い方でのメモリ解放をどうにかして実施できないかと思っています。
例)
※全て同プロジェクト内です。
※名前空間は省きます。
※本来はデータ取得用のGETメソッドなどもあるのですが省きます。
class A{
B b;
A(){ b = new B(); }
public void add(string s){ b.add(s); }
public del(){ }
↑ここでBのcやCのsDataを処分してメモリを解放したいです。b=nullとか?
}
class B{
C c;
public B(){ c = new C(); }
public void add(string s){ c.add(s); }
}
class C{
List<string> sData;
public C(){ sData = new List<string>(); }
public void add(string s){ sData.add(s); }
}
最初からList<string>をAで持てば、という点については、無しにして頂ければと思っています。
また、DLLの呼び出し元にあまり手の込ませた手順を入れなくて済むようにしたいため、ドメインのアンロードで解消は除外でお願いします。(アンロードでは解消しない、的外れな意見でしたらすみません)
そもそも、インスタンスクリア後に呼び出し元に戻った時点で、GCの自動稼働で解決するよ、などありましたらそれもお教え下さい。
Aクラス内で、C c = b.c; c.sDataに何かしたら良い?などがあるのかもしれません。そこも私の方でよく分かっていません。
お手数ですが、ご教授頂ければと思います。
No.2ベストアンサー
- 回答日時:
任意削除なら
A(){ b = new B(); }
public del(){ b = new B(); }
でも良いですよ。というか使うたびに if(b==null) とか無駄なので上記が推奨です。
要点は new B(); ではなく b= の部分です。
b=nullに限らず、変数bに何か新しく代入すれば、bがそれまで参照していたオブジェクトは参照を失うためアクセス不能になりガーベージコレクションの対象となります。
# 繰り返しますが、他に生きた参照がある場合は別です
回答ありがとうございます。
newでも解放に至ってくれるのですね。
newは空ではなくて、改めて作る、の印象で、メモリは残ってしまうものと思っていました。
確かにこれならdel後に呼び出し元から再度addをやってもbが空で呼べないは無いですね。
助かりました。感謝です。
No.1
- 回答日時:
del()って普通のメンバ関数ですよね。
間違って呼び出してバグになるだけなので止めた方が良いでしょう。解放処理を書くならデストラクタ~A()を定義してその中でしょうけど、単なるメモリ解放ならガーベージコレクタの領分なのでやる必要ないです。オブジェクトが開いていたファイルを閉じるとか、そういった処理を行ないます。あと他のオブジェクトの中まで触るような書き方をすると呼び出されるタイミングとか順序の問題でバグの原因となりかねないので余計な処理は書かない方が良いです。
ガーベージコレクタがある言語においてオブジェクトはプログラムからアクセスする手段がなくなるとガーベージコレクションの対象となります。質問の例だとクラスAのオブジェクトへのリンクをクリアした時点でその配下にあるb,c,sDataの全オブジェクトが回収対象になりそのうち回収されるでしょう。
# 他に生きた参照がある場合は別です
回答ありがとうございます。
GCでどうにかなるものなのですね。
del()については、呼び出し元任意でデータ削除を行いたいのです。
また、呼び出し元はクラスAのインスタンス破棄をしないため、デストラクタでは難しいのです。
ですので、例のコードが甘かったのですが、クラスAではコンストラクタを辞め、b.add前に「if(b == null) b = new B();」を追加のイメージになります。
ちなみに、del側はb=nullでGCによるメモリ解放はされますか?newをするのはメモリ解放に繋がらない考えでいます。認識違いでしたらすみません。
お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!
似たような質問が見つかりました
- Java java final 1 2022/06/10 22:49
- Java JavaのSingletonパターンのprivateの持つ意味が分かりません。 5 2022/06/12 10:38
- Java java 入力 3 4 3 出力 ABC DEFG HIJ このようなプログラムの書き方を教えてくだ 2 2022/07/15 14:18
- C言語・C++・C# C# DatagridviewにExcelシートを反映するとエラーが出る 2 2023/05/06 17:12
- C言語・C++・C# クラスのメンバ変数を基準に並べ替えをしたい 5 2022/12/25 17:40
- Java javaのクラスの分け方について質問です。 APIの内部用と外部用でクラスを分けたいのですがインター 2 2022/04/26 16:06
- C言語・C++・C# 大量のデータを読み込んで表示する速度を改善したい 8 2023/05/07 13:29
- Java Java プログラム public class Main { public static void 3 2023/08/10 23:46
- Java リレーションエンティティクラスとは何ですか? 2 2023/02/10 00:02
- Java javaでのプログラム(配列)について質問です. 2 2022/10/14 22:27
関連するカテゴリからQ&Aを探す
デイリーランキングこのカテゴリの人気デイリーQ&Aランキング
-
オブジェクト型の変数が定義さ...
-
ボタンを押すとラベルの文字を...
-
CreateObjectとはどういう意味...
-
すべてのページにServer.Create...
-
【VC++6.0(MFC)】「Out of memo...
-
メモリリークが発生するのはど...
-
C# panel内のコントロールの使...
-
コンストラクタ内でのthisポインタ
-
既定のコンストラクタがない?
-
エディットコントロールのイベ...
-
条件によって別のクラスのイン...
-
FriendとPublicの違い。。。
-
ダイアログクラスのコントロー...
-
関数の呼び出し元の検索
-
リストコントロールをウィンド...
-
C# フォームのShow()のオーバー...
-
MFCでSDIからダイアログの呼び出し
-
EditViewクラス 文字色の変更...
-
ダイアログ表示時にチェックボ...
-
イベントにAddHandlerされてい...
マンスリーランキングこのカテゴリの人気マンスリーQ&Aランキング
-
CreateObjectとはどういう意味...
-
オブジェクト型の変数が定義さ...
-
C# panel内のコントロールの使...
-
最小化したフォームを元に戻す
-
メモリリークが発生するのはど...
-
クラス内にWin32APIのコールバ...
-
イベントドリブンとオブジェク...
-
Visual studio c# android オブ...
-
関数で値渡しと参照渡しではど...
-
C#でのUNZIP32.DLLの利用方法が...
-
ゆかりネットで東北ずん子exを...
-
VB6では、Applicationは未定義...
-
C#でのコンパイル時のエラー
-
SetとNothingの存在意味?
-
メモリ解放について、ご教授く...
-
STLの質問です
-
C#でExcelを起動したい
-
ボタンを押すとラベルの文字を...
-
Disposeはするべきですか?
-
UMLでの「オブジェクト」と「イ...
おすすめ情報