一 Java 线程状态
1 图解
2 代码
package com.mashibing.juc.c_000;
// 线程的状态
public class T04_ThreadState {
static class MyThread extends Thread {
@Override
public void run() {
System.out.println(this.getState());
for(int i=0; i<10; i++) {
try {
Thread.sleep(500);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println(i);
}
}
}
public static void main(String[] args) {
Thread t = new MyThread();
System.out.println(t.getState());
t.start();
try {
t.join();
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println(t.getState());
}
}
3 测试
NEW
RUNNABLE
0
1
2
3
4
5
6
7
8
9
TERMINATED
二 方法调用和启动线程区别
1 代码
package com.mashibing.juc.c_000;
import java.util.concurrent.TimeUnit;
public class T01_WhatIsThread {
private static class T1 extends Thread {
@Override
public void run() {
for (int i = 0; i < 10; i++) {
try {
TimeUnit.MICROSECONDS.sleep(1);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("T1");
}
}
}
public static void main(String[] args) {
// new T1().run(); // 方法调用
new T1().start(); // 启动一个新线程
for (int i = 0; i < 10; i++) {
try {
TimeUnit.MICROSECONDS.sleep(1);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("main");
}
}
}
2 方法调用测试
T1
T1
T1
T1
T1
T1
T1
T1
T1
T1
main
main
main
main
main
main
main
main
main
main
3 启动线程测试
T1
main
T1
main
T1
main
T1
main
T1
main
T1
main
T1
main
main
T1
T1
main
main
T1
三 创建和启动线程
1 代码
package com.mashibing.juc.c_000;
// 创建和启动线程
public class T02_HowToCreateThread {
static class MyThread extends Thread {
@Override
public void run() {
System.out.println("Hello MyThread!");
}
}
static class MyRun implements Runnable {
@Override
public void run() {
System.out.println("Hello MyRun!");
}
}
public static void main(String[] args) {
new MyThread().start(); // 通过继承 Thread 创建和启动线程
new Thread(new MyRun()).start(); // 通过实现 Runnable 创建和启动线程
new Thread(() -> {
System.out.println("Hello Lambda!");
}).start(); // 通过 Lambda 表达式创建和启动线程,它实际是第2种的变形
}
}
// 启动线程的三种方式
// 1:Thread
// 2:Runnable
// 3:Executors.newCachedThread 通过线程池启动线程
2 测试
Hello MyThread!
Hello MyRun!
Hello Lambda!
四 线程的几个常用方法
1 点睛
sleep:当前线程睡眠一段时间,让给其他线程去执行。
yield:当前线程非常谦让地退出一下,进入到就绪状态,随时可能再次运行。
join:比如在t2线程中,调用t1.join。它的意思是,让t1线程先运行完,然后继续执行t2线程。它的应用场景:等待另外一个线程的结束。
2 代码
package com.mashibing.juc.c_000;
// 测试线程的几个常用方法
public class T03_Sleep_Yield_Join {
public static void main(String[] args) {
testSleep();
//testYield();
//testJoin();
}
static void testSleep() {
new Thread(() -> {
for (int i = 0; i < 10; i++) {
System.out.println("A" + i);
try {
Thread.sleep(500);
//TimeUnit.Milliseconds.sleep(500)
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}).start();
}
static void testYield() {
new Thread(() -> {
for (int i = 0; i < 10; i++) {
System.out.println("A" + i);
if (i % 2 == 0) Thread.yield();
}
}).start();
new Thread(() -> {
for (int i = 0; i < 10; i++) {
System.out.println("------------B" + i);
if (i % 2 == 0) Thread.yield();
}
}).start();
}
static void testJoin() {
Thread t1 = new Thread(() -> {
for (int i = 0; i < 10; i++) {
System.out.println("A" + i);
try {
Thread.sleep(500);
//TimeUnit.Milliseconds.sleep(500)
} catch (InterruptedException e) {
e.printStackTrace();
}
}
});
Thread t2 = new Thread(() -> {
try {
t1.join();
} catch (InterruptedException e) {
e.printStackTrace();
}
for (int i = 0; i < 10; i++) {
System.out.println("B" + i);
try {
Thread.sleep(500);
//TimeUnit.Milliseconds.sleep(500)
} catch (InterruptedException e) {
e.printStackTrace();
}
}
});
t1.start();
t2.start();
}
}
3 测试
a sleep 测试结果
A0
A1
A2
A3
A4
A5
A6
A7
A8
A9
b yield 测试结果
A0
A1
A2
A3
A4
------------B0
A5
A6
A7
A8
A9
------------B1
------------B2
------------B3
------------B4
------------B5
------------B6
------------B7
------------B8
------------B9
c join 测试结果
A0
A1
A2
A3
A4
A5
A6
A7
A8
A9
B0
B1
B2
B3
B4
B5
B6
B7
B8
B9