2017-03-25 33 views
2

スレッドの問題を抱えていますが、これがどうなるのか、間違ってコード化されているのか分かりません。私が理解していることから、スレッド化は複数のメソッドを同時に実行する必要があり、そのためにスレッド化されている必要があります。私のコードは1回のチャーを取って1000回繰り返すことになっていますが、2回の文字のバリエーションを変えるのではなく、千回、 "千回"、 "千回"です。私の問題は何ですか?スレッドが正しく動作していませんか?

メインメソッド

import java.util.*; 
public class MainThread { 

    public static void main(String[] args) { 
     // TODO Auto-generated method stub 

     Scanner answer = new Scanner(System.in); 

     System.out.println("Give me a single character: "); 
     char h = answer.next().charAt(0); 
     System.out.println("Give me another single character: "); 
     char a = answer.next().charAt(0); 

     MyThread t1 = new MyThread(h); 
     MyThread t2 = new MyThread(a); 

     t1.start(h); 
     t2.start(a);   

     answer.close(); 
    } 
} 

私スレッディングクラス

import java.util.*; 
public class MyThread extends Thread{ 

    Scanner answer = new Scanner(System.in); 

    public MyThread(char x) { 
     // TODO Auto-generated constructor stub 
    } 


    public void Stored(char x){ 
     System.out.println("Type a single letter here: ");  
    } 


    //modified run method 
    public void start(char x){ 

     for(int i = 0; i < 1000; i++){ 
      System.out.print(x); 
      try { 
       Thread.sleep(1); 
      } catch (InterruptedException e) {    
       e.printStackTrace(); 
      } 
      Thread.yield(); 
     } 
    } 
} 
+0

こんにちは、開始メソッドではなく実行メソッドをオーバーライドする必要があります –

答えて

0

まず第一に、あなたが正しいマルチスレッドを実装する場合でも、ご説明した動作は発生しないことを保証していません。しかし、それは繰り返すべきではありません;)

解決策は:start()ではなくrun()メソッドをオーバーライドします。 スレッドコンストラクタは引数を取る必要があります。start()はmainから呼び出され(引数を持つ新しいstartメソッドはありません)、run()は並列に実行されるジョブを実装します。したがって、スレッドコンストラクタで設定したスレッドのフィールドにアクセスできます。

1

あなたが行っていることは、むしろあなたがstartメソッドを順番に呼ばれている、マルチスレッドではありません、すなわち、平行複数のスレッドを実行するために、あなたはあなたのMyThreadクラスのrun()メソッドをオーバーライドする必要があります。

重要な点は、ときstartスレッド、及びrun()内のコードは、他の/メインスレッドと並行して実行されるので、示されているようMyThreadクラス内run()をオーバーライドするrun()方法が自動的にJVMによって呼び出されることです以下:

class MyThread extends Thread { 

    private char x; 

    public MyThread(char x) { 
     this.x= x; 
    } 

    // Add run() method 
    public void run() { 

     for (int i = 0; i < 10; i++) { 
      System.out.print(x); 
      try { 
       Thread.sleep(500); 
      } catch (InterruptedException e) { 

       e.printStackTrace(); 
      } 
      Thread.yield(); 
     } 
    } 
} 

MainThreadクラス:

public class MainThread { 

    public static void main(String[] args) { 
     // TODO Auto-generated method stub 

     Scanner answer = new Scanner(System.in); 

     System.out.println("Give me a single character: "); 
     char h = answer.next().charAt(0); 
     System.out.println("Give me another single character: "); 
     char a = answer.next().charAt(0); 

     MyThread t1 = new MyThread(h); 
     MyThread t2 = new MyThread(a); 

     t1.start();//this calls run() of t1 automatically 
     t2.start();//this calls run() of t2 automatically   

     answer.close(); 
    } 
} 

は、Threadの作成方法と開始方法、およびマルチスレッドの仕組みに関する基本的な理解を持っていることをお勧めします。

1

スレッドを並列実行させるには、startの代わりにrunメソッドを実装する必要があります。

Thread.start()のJavadocを参照してください:

原因実行を開始するには、このスレッドを。 Java仮想マシンは runこのスレッドのメソッドを呼び出します。 (startメソッドの呼び出しから復帰)現在 スレッドと(そのrunメソッドを実行する) 他のスレッド:

結果は、2つのスレッドが同時に実行されることです。

0

エラーは既に説明されています:startメソッドがrunメソッドの代わりにオーバーライドされています。とにかく、その機能を拡張したくないので、Threadクラスを拡張することはお勧めしません。

あなただけのようにより良いアプローチは、(IMO)スレッドにRunnableをを提供することで、スレッドを使用したい:

public static void main(String[] args) { 
     // ... 
     Thread t1 = new Thread(new MyRunnable(h)); 
     t1.start(); 
    } 

のRunnable(生産コードでより良い名前を使用):

public class MyRunnable implements Runnable { 

    private final char ch; 

    public MyRunnable(char theChar) { 
     ch = theChar; 
    } 

    @Override 
    public void run() { 
     for (int i = 0; i < 1000; i++) { 
      ... 
     } 
    } 

これはラムダで使用して改善することができますが、ポイントはここ

詳細ではありません。"implements Runnable" vs. "extends Thread"

関連する問題