2016-10-02 14 views
0

Here is the java.util.concurrent.FutureTask doc pageここでは、Callable実装クラスを作成せずにラムダ式を使用しています。ここでは、呼び出し可能なインターフェイスの動作をテストしたいだけですが、結果が私には不満です。 new Thread(ft, "会不会执行呢?").start();によって作らマルチタスクを実行するJava Callableインターフェイス

import java.util.concurrent.*; 
public class CallableTest{ 
    public static void main(String[] args){ 
     FutureTask<Integer> ft = new FutureTask<Integer>((Callable<Integer>)() -> { 
      int i = 0; 
      for(; i < 100; i++){ 
       System.out.println(Thread.currentThread().getName() + "\t"+ i); 
      } 
      return i; 
     }); 
     for(int i = 0; i < 100; i++){ 
      System.out.println(Thread.currentThread().getName() + "\t" + i); 
      if(i == 20){ 
       new Thread(ft, "有返回值的线程").start(); 
       new Thread(ft, "会不会执行呢?").start(); 
      } 
     } 
     try{ 
      System.out.println("The result of ft is " + ft.get()); 
     }catch(Exception e){System.out.println(e);} 
    } 
} 

結果ショーのスレッドは関係なくイテレータ回を実行しない100または何でもでした。それが理由です?私はこの質問を探せたが、彼らはすべてThreadPoolを使用して言ったが、私はこれらの2つの単純なスレッドがスレッドプールを動作させることができないと思う。

答えて

2

FutureTaskは、次の遷移がstateを維持:

* Possible state transitions: 
* NEW -> COMPLETING -> NORMAL 
* NEW -> COMPLETING -> EXCEPTIONAL 
* NEW -> CANCELLED 
* NEW -> INTERRUPTING -> INTERRUPTED 

状態がNEWされていない場合、それはrun方法だだけ返します。

public void run() { 
     if (state != NEW || 
      !UNSAFE.compareAndSwapObject(this, runnerOffset, 
            null, Thread.currentThread())) 
      return; 
     .... 
    } 

をので、別FutureTaskインスタンスはスレッドごとに必要とされていますftは、最初のスレッド実行後にはNEWではない状態です。

次のコードは、両方のスレッドを実行します。

import java.util.concurrent.Callable; 
    import java.util.concurrent.FutureTask; 

    public class FutureTask { 

    public static void main(String[] args) { 
     FutureTask<Integer> ft = getFutureTask(); 
     FutureTask<Integer> ft2 = getFutureTask(); 
     new Thread(ft, "有返回值的线程").start(); 
     new Thread(ft2, "会不会执行呢?").start(); 
     try{ 
      System.out.println("The result of ft is " + ft.get()); 
     }catch(Exception e){System.out.println(e);} 
     try{ 
      System.out.println("The result of ft2 is " + ft2.get()); 
     }catch(Exception e){System.out.println(e);} 
    } 

    private static FutureTask<Integer> getFutureTask() { 
     return new FutureTask<Integer>((Callable<Integer>)() -> { 
      int i = 0; 
      for(; i < 100; i++){ 
       System.out.println(Thread.currentThread().getName() + "\t"+ i); 
      } 
      return i; 
     }); 
    } 
+0

私は複数のFutureTaskインスタンスがTask.eh 1のために提供されていないため、各タスクのたびに、それはマルチスレッドのように定義すべきではないFutureTaskをインスタンス化する必要がある場合は、ここで私はあなたの答えにいくつかの修正をしたい、私はCallableインターフェイスが実装されていると思うし、それぞれのFutureTaskは、コンストラクタパラメータとして、この実装を入れて、大丈夫、マルチスレッドのアイデアが表示されます。 – Crabime

関連する問題