2011-12-10 9 views
0

スレッドが完了した後にThreadオブジェクトの状態を理解しようとしています。スレッドがrun()メソッドを完了すると、スレッドオブジェクトは依然として有効なオブジェクトであり、それでもインスタンスオブジェクトとして使用でき、それでもメソッドを呼び出せるという本を読みました。私は以下の例でこれを試してみることにしました:join()を使って他の3つのスレッドが完了するのを待ちます。次に、cのrun()メソッドを呼び出しますが、何らかの理由でrun()メソッドから何も出力されません。上記のプログラムを実行した後の出力の最後の数行がここにあります。スレッドが完了した後でスレッドのrun()メソッドを実行する

y is 287 
y is 287 
y is 288 
y is 289 
      Thread-1 
      Thread-0 
y is 289 
y is 289 
y is 290 
y is 291 
      Thread-1 
      Thread-0 
y is 291 
y is 291 
y is 292 
y is 293 
      Thread-1 
      Thread-0 
y is 293 
y is 293 
y is 294 
y is 295 
      Thread-0 
y is 295 
y is 296 
      Thread-0 
y is 296 
y is 297 
      Thread-0 
y is 297 
y is 298 
      Thread-0 
y is 298 
y is 299 
      Thread-0 
y is 299 
y is 300 
Running C's Run 

スレッドが完了しても、私はc.run()呼び出しのためにyの値が400になると予想していました。

アイデア?

ありがとうございます。

+1

d.run()を呼びたくないのですか?また、3つのスレッドが同じ変数をインクリメントしてロックがない場合、何も壊れていないことに驚いています。 – Thomas

+0

はいスレッドオブジェクトが完了したらそれを実行したかったのです。 – ziggy

答えて

1

オブジェクトの状態に

+0

Thread.exitがターゲットにnullを割り当てる場合、ターゲットのrunメソッドを呼び出すとNullPointerExceptionが発生しませんか?私はスレッド完了後にd.run()を呼び出そうとしましたが、この時点でオブジェクトがnullになっていても、NullPointerExceptionを取得しませんでした。 – ziggy

+0

あなたはNPEを手に入れません。私の第2段落をもう一度読んで...特に、「ターゲット」が「ヌル」の場合については何を言いますか。さらに、スレッドクラスのソースコードを自分で見てみましょう。 –

+0

* Oracleが引き継いで以来、Stephenは1.0.2からのバグで、バグ参照をたくさん削除しました。私は99年のコードを覚えていますが、まだ同じです。いずれにせよ、積極的な除去は糸漏れなどのためにgcを助けていました。スレッドがまだ漏洩しているので、今はまだクールです。 – bestsss

3

スレッドクラスを拡張するとうまくいくはずです。今、それはあなたが観察している何のための理由がThreadの実装に埋設されているThread.exit後nullあるRunnableターゲット()DieThread

synchronized(this) { 
    System.out.println("    " + Thread.currentThread().getName()); 
    System.out.println("y is " + y); 
    y++; 
    System.out.println("y is " + y); 
} 
1

同期アクセスをチェックしますクラス。

c.run()を呼び出すと、スレッドオブジェクトに対してrunメソッドが呼び出されます。これは、nullではない場合、targetオブジェクトのrunメソッド(つまり、Threadコンストラクタで提供される実行可能オブジェクト)を呼び出すように指定されています。 targetnullの場合、Thread.run()メソッドは何も行いません。

OK、nullを指定しなかったのでtargetを指定しました。

実際、Threadが終了すると、Thread.exit()メソッドが呼び出されてクリーンアップされます。クリーンアップが行うことの1つは、nulltargetに割り当てることです。 (コードには積極的に参照をクリアする必要があるというコメントとバグIDがありますが、残念ながら対応するバグレポートがありませんので、実際の理由を知ることはできません)

とにかく、最終行は、Thread.run()を呼び出すことによってターゲットオブジェクトのrun()メソッドを再実行できないということです。ターゲット参照がある場合は、ターゲットオブジェクトのrun()メソッドを直接呼び出すことができます。

+0

ありがとうございます。私は実際にオブジェクトの状態を心配していませんでした。私は、スレッドがスレッドとして完了した後に何が起こるかにもっと興味があります。 – ziggy

関連する問題