スレッドを作成するには、Oracleの公式ドキュメント
-
Java SE 8 API文档: docs.oracle.com/javase/8/do…
java.lang.Threadのクラスのドキュメントを参照してください。
-
- このクラスは、Threadのサブクラスとして宣言し、runメソッドをオーバーライドしています。
官方原话:実行の新しいスレッドを作成するには、2つの方法があります。一つは、のサブクラスであるクラスを宣言することです
Thread
。このサブクラスは、オーバーライドする必要がありrun
、クラスのメソッドをThread
。/** * 实现线程的第一个方式 继承Thread * @author yiren */ public class MyThread extends Thread { @Override public void run() { System.out.println(Thread.currentThread().getName() + " Thread running..."); } public static void main(String[] args) throws IOException { new MyThread().start(); System.in.read(); } } 复制代码
-
- runメソッドを達成し、実装するために、Runnableインタフェース。
官方原话:スレッドを作成するもう1つの方法は、実装するクラスを宣言することである
Runnable
インターフェイス。そのクラスは、実装run
方法を。
/**
* 实现线程的第二个方式 实现Runnable接口
* @author yiren
*/
public class MyRunnable implements Runnable {
@Override
public void run() {
System.out.println(Thread.currentThread().getName() + " Runnable running...");
}
public static void main(String[] args) throws IOException {
new Thread(new MyRunnable()).start();
System.in.read();
}
}
复制代码
2つの髪の方法の長所と短所
-
- コードの構造を検討するまで、タスクの特定のスレッドの実行方法は、コードを実行することです、コードはビジネスに相当し、それはデカップリングと私たちのスレッドを作成する必要があります。
- 相続した場合
Thread
、あなたは非同期タスクを構築したいたびに、私たちは別のスレッドを確立する必要があります。そして、糸の消費量を作成することは、あなたが使用している場合は、比較的大きいRunnable
、我々は大幅にスレッドを作成するために、損失や破壊を減らすことができ、スレッドプール、などのツールをうまく利用して取得することができます。資源保存。 - Javaは継承された単一継承であるため、
Thread
クラスの後、あなたは非常に拡張性を制限し、他のクラスから継承することはできません。
/* What will be run. */
private Runnable target;
public Thread(Runnable target) {
init(null, target, "Thread-" + nextThreadNum(), 0);
}
private void init(ThreadGroup g, Runnable target, String name,
long stackSize) {
init(g, target, name, stackSize, null, true);
}
private void init(ThreadGroup g, Runnable target, String name,
long stackSize, AccessControlContext acc,
boolean inheritThreadLocals) {
......
this.target = target;
......
}
@Override
public void run() {
if (target != null) {
target.run();
}
}
复制代码
-
二つの方法の性質(上記のスレッドクラスのソースコードから参照されたいです)
- 継承は、
Thread
全体れるrun()
方法が上書きされます - 達成
Runnable
最終的に方法がされて呼び出さRunnable
run
target.run()
- 継承は、
-
両方の方法は、それの影響がどうなるかある場合は?
/** * @author yiren */ public class MyThreadAndRunnable { public static void main(String[] args) { Thread thread = new Thread(new Runnable() { @Override public void run() { System.out.println(Thread.currentThread().getName() + " runnable running..."); } } ) { @Override public void run() { System.out.println(Thread.currentThread().getName() + " thread running..."); } }; // 这个地方应该是执行重写Thread类的run方法中的逻辑! thread.start(); } } 复制代码
- もちろん、上記オーバーライドしないと述べたメソッドが呼び出され、それ書き換える一切の呼び出しがない場合は、。
Thread
run()
target.run()
target.run()
- もちろん、上記オーバーライドしないと述べたメソッドが呼び出され、それ書き換える一切の呼び出しがない場合は、。
-
正確には、一方向だけのスレッドを作成し、それはビルドすることです
Thread
2を超えると言うことですつまり、2つの方法がありますが、スレッド実行ユニットをクラス、および達成。
その他のバージョン:
-
スレッドプールのスレッドを作成します。
/** * wrong 线程池创建 * * @author yiren */ public class ThreadPoolExample { public static void main(String[] args) { ExecutorService executorService = Executors.newCachedThreadPool(); for (int i = 0; i < 1000; i++) { executorService.submit(() -> { try { Thread.sleep(500); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println(Thread.currentThread().getName()); }); } } } // Executors中的DefaultThreadFactory static class DefaultThreadFactory implements ThreadFactory { private static final AtomicInteger poolNumber = new AtomicInteger(1); private final ThreadGroup group; private final AtomicInteger threadNumber = new AtomicInteger(1); private final String namePrefix; DefaultThreadFactory() { SecurityManager s = System.getSecurityManager(); group = (s != null) ? s.getThreadGroup() : Thread.currentThread().getThreadGroup(); namePrefix = "pool-" + poolNumber.getAndIncrement() + "-thread-"; } public Thread newThread(Runnable r) { Thread t = new Thread(group, r, namePrefix + threadNumber.getAndIncrement(), 0); if (t.isDaemon()) t.setDaemon(false); if (t.getPriority() != Thread.NORM_PRIORITY) t.setPriority(Thread.NORM_PRIORITY); return t; } } 复制代码
- うち
newThread()
、既知の方法、でもスレッドプールは、本質的に、使用されThread
たスレッドを作成します。
- うち
-
呼び出し可能とFutureTaskは、スレッドを作成します
-
UML図は、上記スレッドとRunnableを内側から見た、または実際に達成するために使用します。
-
タイマタイマ
/** * @author yiren */ public class TimerExample { public static void main(String[] args) { Timer timer = new Timer(); // 每隔1s打印下自己的名字 timer.scheduleAtFixedRate(new TimerTask() { @Override public void run() { System.out.println(Thread.currentThread().getName() + " timer running..."); } }, 1000, 1000); } } 复制代码
- それは実際に、Runnableインタフェースを実装しTimerTaskを、あなたは見ることができ
TimerTask
、この抽象クラス
- それは実際に、Runnableインタフェースを実装しTimerTaskを、あなたは見ることができ
-
匿名内部クラス、ラムダ式(本質は同じです)
/** * 匿名内部类 * @author yiren */ public class AnonymousInnerClassExample { public static void main(String[] args) { new Thread() { @Override public void run() { System.out.println(Thread.currentThread().getName()); } }.start(); new Thread(new Runnable() { @Override public void run() { System.out.println(Thread.currentThread().getName()); } }).start(); } } /** * lambda表达式 * @author yiren */ public class LambdaExample { public static void main(String[] args) { new Thread(() -> System.out.println(Thread.currentThread().getName())).start(); } } 复制代码
私について
- 杭州、通常の学部読み取り、コンピュータ科学と技術的専門知識、20年の卒業をコーディネート。
- 主にJava開発を行って、Golang、シェルについて書きます。マイクロサービス、ビッグデータはこの方向に行う準備ができ、興味を持って。
- あなた首長光スプレーは狂った兄が学習され、新人段階に現在あります。
- メッセージ交換を残すようこそ!!!