2011-01-25 17 views
2

私はかなり大量のデータで動作する標準のCRUDアプリケーションを持っています。異なるウィンドウはLinq-To-SQLを使って異なるテーブルにアクセスし、各ウィンドウは本質的に私が表示しているオブジェクトにバインドされたセルを持つグリッドを持っています。ここでウィンドウがガベージコレクションされないのはなぜですか?

が起こっているのはかなり標準的な使用のケースです:

  1. オープンウィンドウA
  2. ウィンドウを閉じるA - ウインドウAがメモリにまだ今ではありませんが、見えなく。
  3. ウィンドウを開くB
  4. ウィンドウを閉じるウィンドウB - ウィンドウAとBは両方ともメモリにあり、どちらも表示されません。
  5. オープンウィンドウC
  6. ウィンドウCのデータが取得されると、ウィンドウAのリソースが解放されます。

いつでも私は実際に持っているべきであるときに私は2-3の窓を記憶に持っています。私はnullに考えることができるすべての参照を設定するこれらのウィンドウの終了イベントに廃棄コードを追加しました。

私はANTSメモリプロファイラを使ってみましたが、各ウィンドウがGCルートとして設定されていることに気付いています。この動作を無効にする方法がありますか、または何らかの理由でGCがこれらのウィンドウから収集するように強制しますか?

ありがとうございます!

PS:this linkを確認しても問題は解決しませんでした。

編集:問題は、ユーザーがSystem.OutOfMemoryExceptionsを取得していることです。

答えて

2

これを2つのアップデートで修正できました。まず、私は子供の窓にTelerikコントロールを使っていました。 Telerikコントロールはルートビジュアルを追跡する必要があるため、子ウィンドウでのみインスタンス化されている場合は、各インスタンスで子ウィンドウがルートビジュアルであると想定し、静的参照を割り当てます。メインのアプリケーションウィンドウでtelerikコントロールをインスタンス化することによって、そのウィンドウは静的参照のルートビジュアルとして設定されました。

私が作成した2番目の更新は、各子ウィンドウの所有者をメインのアプリケーションウィンドウとして割り当てることでした。これとプロファイリングをした後、私は子ウィンドウがもはやGCルーツとして設定されていないことを発見しました。

私の子供のウィンドウは、別のウィンドウで新しいメモリが要求されるとすぐに、閉じた後に自動的にガベージコレクションを行います。

2

一般的に、GCには自分の人生があります。リソースを解放することで、リソースが不要になったことを通知するだけです。パフォーマンス制約とプラットフォーム固有の実装のために、ガベージコレクションには時間がかかります。

開発者の生活を容易にするものは、パフォーマンスを低下させることがあります。だからC/C++ではあなたが望むようにメモリと新しい/削除を所有することができます。そしてそこにもプールや他のテクニックがあり、新しい/削除を引き起こす原因は安くはありません。

最後に、アーキテクチャの問題を特定する必要があります。なぜこれはあなたにとって問題なのですか?メモリから抜け出す?スワッピング?ローカルまたはサーバー上で?その他

+0

"一般的にGCには自分の人生があります。" - 私がGC.Collect()を呼び出すときでさえ、リソースを解放しません。何かがこれらのリソースを保持しているかのようですが、これを行う可能性はわかりません。これらのオブジェクトは収集する必要があります - 私はプロファイラーでこれを検証しました。問題は、各ウィンドウがGCルートであることと関係があると仮定していますが、 WPF。 – Jake

+0

元の投稿から、リソースは解放されたようですが、GC.Collect()を呼び出した直後ではないようです。 – Zepplock

+0

GC.Collect()はリソースを解放していないようです。私がこのメソッドを呼んでいないときに解放されるのと同じ時期に、ずっと遅くなってしまいます。 – Jake

関連する問題