クラスインスタンスがガベージコレクターによって収集されるたびにfinalize()が呼び出されることを私は知っています。ただし、クラスのインスタンスをキューを介して別のスレッドに渡すときは、少し混乱します。
これがThread1のスケルトンであるとしましょう。
for(i=0; i<1000; i++) {
Packet pkt = new Packet(); // instance of class
pkt.id = i;
thread2.queue.put(pkt);
}
次に、スレッド2はパケットをキューから削除し、長時間の操作を実行します。この2番目のスレッドはパケットの「コピー」を取得しますか、それとも何らかの参照によるものですか?重要なのは、コピーによる場合、スレッド1で作成されたインスタンスのfinalize()は、スレッド2がパケットを処理する前に呼び出すことができるということです。参照による場合、finalize()はパケット内の情報に対して1回だけ呼び出されることが保証されています。
この基本的な例は重要性を示していないかもしれませんが、オブジェクトを使い終わったときにメモリを破壊するために、(JNIからの)Cポインターをパケットに格納しています。コピーで渡された場合、2番目のスレッドが完了する前にメモリが破壊される可能性があります。参照によって渡された場合は、GCが両方のスレッドで使用されなくなったことを確認した後でのみ破棄する必要があります(私の望ましい動作)。この後者のシナリオが保証されていない場合は、finalize()を使用せず、他の何かを使用しますが、より複雑になります。