進入到TimeWaiting(計時等待)有兩種方式:
1.使用sleep(long m)方法,在毫秒值結束之後,線程睡醒進入到Runnable/Blocked(運行/阻塞)狀態
2.使用wait(long m)方法,wait方法如果在毫秒值結束之後,還沒有被notify喚醒,就會自動醒來,線程睡醒進入到Runnable/Blocked狀態
wait(long m)喚醒的方法
①void notify() 喚醒在此對象監視器上等待的單個線程(隨機喚醒)。
public class WaitAndNotify {
public static void main(String[] args) {
// 創建鎖對象,保證唯一
Object obj = new Object();
// 創建第一個顧客線程
new Thread(){
@Override
public void run() {
while (true){
// 保證等待和喚醒只能有一個執行,需要同步技術
synchronized (obj){
System.out.println("顧客1告知老闆要的包子的種類和數量");
// 調用wait方法,放棄cpu的執行,進入到WAITING狀態(無限等待)
try {
obj.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
// 被喚醒後的代碼
System.out.println("顧客1取餐喫包子");
System.out.println("-----------------------------------");
}
}
}
}.start();
// 創建第二個顧客線程
new Thread(){
@Override
public void run() {
while (true){
// 保證等待和喚醒只能有一個執行,需要同步技術
synchronized (obj){
System.out.println("顧客2告知老闆要的包子的種類和數量");
// 調用wait方法,放棄cpu的執行,進入到WAITING狀態(無限等待)
try {
obj.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
// 被喚醒後的代碼
System.out.println("顧客2取餐喫包子");
System.out.println("-----------------------------------");
}
}
}
}.start();
// 創建一個老闆線程(生產者)
new Thread(){
@Override
public void run() {
while (true){
// 用5秒做包子
try {
Thread.sleep(5000);
} catch (InterruptedException e) {
e.printStackTrace();
}
// 保證等待和喚醒的線程只能有一個執行,需要使用同步技術
synchronized (obj){
System.out.println("老闆5秒鐘之後做好包子,告知顧客可以喫包子了");
// 做好包子之後,調用notify方法,喚醒顧客喫包子
obj.notify();
}
}
}
}.start();
}
}
運行結果:
②void notifyAll() 喚醒在此對象監視器上等待的所有線程。
public class Demo3WaitAndNotify {
public static void main(String[] args) {
// 創建鎖對象,保證唯一
Object obj = new Object();
// 創建第一個顧客線程
new Thread(){
@Override
public void run() {
while (true){
// 保證等待和喚醒只能有一個執行,需要同步技術
synchronized (obj){
System.out.println("顧客1告知老闆要的包子的種類和數量");
// 調用wait方法,放棄cpu的執行,進入到WAITING狀態(無限等待)
try {
obj.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
// 被喚醒後的代碼
System.out.println("顧客1取餐喫包子");
System.out.println("-----------------------------------");
}
}
}
}.start();
// 創建第二個顧客線程
new Thread(){
@Override
public void run() {
while (true){
// 保證等待和喚醒只能有一個執行,需要同步技術
synchronized (obj){
System.out.println("顧客2告知老闆要的包子的種類和數量");
// 調用wait方法,放棄cpu的執行,進入到WAITING狀態(無限等待)
try {
obj.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
// 被喚醒後的代碼
System.out.println("顧客2取餐喫包子");
System.out.println("-----------------------------------");
}
}
}
}.start();
// 創建一個老闆線程(生產者)
new Thread(){
@Override
public void run() {
while (true){
// 用5秒做包子
try {
Thread.sleep(5000);
} catch (InterruptedException e) {
e.printStackTrace();
}
// 保證等待和喚醒的線程只能有一個執行,需要使用同步技術
synchronized (obj){
System.out.println("老闆5秒鐘之後做好包子,告知顧客可以喫包子了");
// 做好包子之後,調用notifyAll方法,喚醒所有顧客喫包子
obj.notifyAll();
}
}
}
}.start();
}
}
運行結果:
線程間通信