、どのような
1. Javaはマルチスレッドのアプローチを作成します
。スレッド、結果は行われず、データも異常でもありません
B。ThreadPoolの、スレッドの作成と破壊のオーバーヘッドを削減
この方法は、得られる結果を返す場合、スレッドは変数通信;. C Runnableを、唯一のrun()メソッドを使用または共有することができる、結果が行われず、実行スレッドであります
D。呼び出し可能な、唯一の()メソッドの呼び出し、Runnableを添加し、戻り値が存在する異常である、一般的な結果を返します
すなわち、非同期計算のための未来、結果として、氏の資格情報ではなく、次の操作がブロックされていない場合、取得結果の資格情報を
2. FutureTask今後のクラスは、インタフェース、今後の基本的な実装を実装します
3.例をパラメータとして呼び出し可能FutureTask、スレッドを開始する引数として、Runnableを本例のように、FutureTaskのインスタンスを作成することができ
二、どのように
戻り値を得るために提出する()メソッドでExecutorServiceの1.呼び出し可能インタフェース、
非同期動作が完了した場合、get()メソッドは、非同期のために、結果を返す参照2.今後インターフェース、isDone()メソッド
3. FutureTask类
A。、Runnableインタフェースと今後インターフェース、非同期の組み合わせを実装し、関数の結果を返します
むしろに戻るよりも、最終的な戻り値ピック-get()メソッド、;値を返すが、内部は呼び出し可能のRunnableに変換される; B FutureTaskは、戻り値が実行可能ではないオブジェクト
。コールバック関数は、タスクの終了時にトリガされ、()が行われているC;この機能がないと今後、タスクが手動でのみ終了するかどうか、そして次に判断できます
第三に、利用シナリオ(とき)
1.時間のかかる計算を、メインスレッドは、そのタスクを完了した後、サブスレッドの結果を取得します
並行性の高い環境下では2回のみ、このようなデータベースリンクの設定など
四、なぜ(原則)
現在のスレッドの状態を表す1 FutureTask状態フィールド、
* 可能な状態遷移: * NEW - >補完----------------- - > NORMAL * NEW - >補完----------------- - > EXCEPTIONAL * NEW - > CANCELED * NEW - >中断- > INTERRUPTED * / プライベート 揮発 int型状態。 プライベート 静的 最終 int型 NEW = 0 ; プライベート 静的 最終 int型 = 1を完了しました。 プライベート 静的 最終 int型 NORMAL = 2 ; プライベート 静的 最終 int型EXCEPTIONAL = 3 。 プライベート 静的 最終 int型 = 4 CANCELED 。 プライベート 静的 最終 int型の中断= 5 ; プライベート 静的 最終 int型 INTERRUPTED = 6;
2. FutureTask run()メソッドのソースコードは、ロジックが呼呼び出し可能main()メソッドを実行することで、結果はRunnableをパッケージに相当する、グローバル変数に格納されます。
公共 ボイドRUN(){ IF(国家NEW = ||! UNSAFE.compareAndSwapObject(!これ、runnerOffset、 ヌル、にThread.currentThread())) リターン; 試み{ 呼び出し可能 <V> C =コーラブル; // 呼び出し可能はここにあります後継の内側から構築する方法であって、例としてはFutureTask Runnableを、最終的に呼び出し可能な使用であるが IF(C =!ヌル &&状態== NEW){ V結果を、 ブールRAN; 試み{ 結果 = c.callを(); RAN = trueに; } キャッチ(ThrowableのEX){ 結果 = ヌル; RAN = falseに、 setException(EX); //は直接スローするのではなく、スローされたコール例外保存 } のIF (RAN) SET(結果); / / メソッド呼び出しの結果を保存 } } 最後に{ // 状態になるまでランナーはnull以外は、に定住しなければなりません // 防ぐ同時が(RUNに呼び出し) ランナー= nullを。 // 状態を防ぐために、ヌルランナー後に再読み込みする必要があります // 漏洩した割り込み int型 S = 状態。 場合(S> = 中断) handlePossibleCancellationInterrupt(S); } }
3. get()メソッドのソースコード、私はグローバル変数からの結果を得たまで、無限ループ障害物を使用して
公共 Vのget()はスローInterruptedExceptionある、ExecutionException { INT S = 状態; もし(S <= 補完-----------------) S = awaitDone(偽、0L )。 リターン・レポート(複数可)。 } プライベート INT awaitDone(ブールタイミング、長いnanos値)は スローInterruptedExceptionある{ 最終 長い時限期限= System.nanoTimeの()+ nanos値:0L ; WaitNode Q = NULL ; ブーリアン=キューに入れられた偽; 用(;;){ 場合(Thread.interrupted()){ removeWaiter(Q)。 スロー 新しい例外:InterruptedExceptionを(); } INT S = 状態。 場合(S> 補完-----------------){ 場合(Q =!ヌル) q.thread = NULL ; リターン秒; } それ以外の 場合(S ==補完-----------------が)// まだタイムアウトすることはできません )(Thread.yieldを。 それ以外の 場合(Q == nullの) Q = 新しいWaitNode(); それ以外の 場合(!はキューに入れられた) キューに入れられた = UNSAFE.compareAndSwapObject(これ、waitersOffset、 q.next = ウェイター、Q); 他の 場合(タイムアウト){ nanos値 =期限- System.nanoTimeの()。 もし(nanos値<= 0L ){ removeWaiter(Q)。 返しの状態を、 } LockSupport.parkNanos(この、またはnanos)。 } 他 LockSupport.park(本) } }
参考:
https://www.cnblogs.com/cz123/p/7693064.html
https://www.jianshu.com/p/bce9301f1adb