・初期値がおかしい


ダイアログを作成した。
メンバ変数として定義。
別スレッドからアクセスする必要があったので。
ダイアログのメンバ変数がnullでなかったら(表示されていたら)、
publicのメソッドを使って表示を変更するとか、そんな感じで。


そのときの呼び出しもとのコード
-- コード->
m_dlgTest = new dlgTest(); // 生成
m_dlgTest.ShowDialog(); // ダイアログ表示
int n_ret = m_dlgTest.GetResult(); // 結果の取得
m_dlgTest = null; // nullクリア
<- コード --


なにが起きたかというと。
ダイアログクラスのメンバ変数の初期値が
前回動作時の最後の値になる・・・。
それ以外にもなんだか前回の動作内容が残っているような・・・。
これは本当に怪談ですよ。
ほとんどゾンビですよ。


むーって、Webで調べてみたら、
「ダイアログはDispose()しないと開放されません」
って、本当かよ。
完全にC#で閉じた世界でないですかい。


nullクリアの前に「.Dispose()」を入れたらきっちり直りました。
-- コード->
m_dlgTest = new dlgTest(); // 生成
m_dlgTest.ShowDialog(); // ダイアログ表示
int n_ret = m_dlgTest.GetResult(); // 結果の取得
m_dlgTest.Dispose(); // 廃棄 <- ※※重要
m_dlgTest = null; // nullクリア
<- コード --


うーん。
これからは、「.Dispose()」とか「.Close()」とかがある場合は、
どんなクラスでもnullクリアの前に実行すると誓うのでした。


・アプリケーションが終了しない


デバイスを使用するアプリケーションを作成した。
テスト結果を受けて修正をしているときに難解な現象に遭遇。


特定できていない特定の条件で、
アプリケーションが終了しないのである。
モジュールを単体で動かしているときは見た目上終了するが、
プロセスが残存していた・・・、模様。
IDEでデバッグしているときにIDEのタスクマネージャの
「デバッグ中」の表示がいつまでも終わらない。


うんうんうなってデバッグコード入れて、ブレークポイントいれて・・・。


結局、デバイスがエラーを返したときの処理(catch)に問題があった。
catchの中でアクセスクラスのメンバ変数にnullを適用して終わり。
正常時に実行されるClose処理を見てみたら「.Dispose()」とかしている。
ので、catchしたところからClose処理を呼ぶことにした。
ら、解決した。


もう一種類のデバイスも同じような感じ・・・。
アクセスクラスはDLLなのだが、VCとかで作っているのかな?


DLLがVCだったり、相手がデバイスだったら
明示的な終了の指示は必要なんでしょうね。


気お付けようっと。

・デストラクタが実行されない


C#を始めたころにはコンストラクタの下に一生懸命デストラクタを書いて、
その中に終了処理を書いていた。
特定のクラスを生成したり削除(nullクリア)したりしているとなにかおかしい。
後始末がされていない。


調べてみたら、
「デストラクタはガベージコレクタが動作したときに実行されるのでタイミングは不明」
「ファイルを閉じるなどの処理はデストラクタではなくて終了処理を明示的に行いましょう」
って、本当かいな。


デストラクタは使用してはいけないのね。

・時代は変わる


「後片付けはガベージコレクタがやってくれます」
「スコープを外れたら自動で始末されます」
「newしてもdeleteしないでいいのよん」
って、JAVAが言い出した。
C#も大体同じ感じで、
普段は「出したら出しっぱなし」で、
知らないうちにお母さんが片付けてくれているんだ。


そんな現代でも夏の夜の怪談は存在する・・・。
正体がわからない現象は何でも怪談だ。

・昔の話


私が全くのPG新人だったころ、
同じく新人の正面の人は趣味がPGって人だった。
もともと機械系の人間の私にとっては
ほとんど理解の範疇を超えていた。


で、彼にいろいろきいたり教えてもらったわけだが、
今でも覚えているせりふがあって、
「出したものは片付ける」
であった。


ファイルは開いたら閉じる。
えぇと、そのときはCOBOLだったので、
「free」とか「delete」とかは無縁だったはずだけど・・・。