成人免费xxxxx在线视频软件_久久精品久久久_亚洲国产精品久久久_天天色天天色_亚洲人成一区_欧美一级欧美三级在线观看

帶你聊聊 Java 并發(fā)編程之線程基礎(chǔ)

開發(fā) 后端
百丈高樓平地起,要想學(xué)好多線程,首先還是的了解一下線程的基礎(chǔ),這邊文章將帶著大家來了解一下線程的基礎(chǔ)知識。

 01、簡介

百丈高樓平地起,要想學(xué)好多線程,首先還是的了解一下線程的基礎(chǔ),這邊文章將帶著大家來了解一下線程的基礎(chǔ)知識。

[[281525]]

02、線程的創(chuàng)建方式

  1. 實(shí)現(xiàn) Runnable 接口
  2. 繼承 Thread 類
  3. 實(shí)現(xiàn) Callable 接口通過 FutureTask 包裝器來創(chuàng)建線程
  4. 通過線程池創(chuàng)建線程

下面將用線程池和 Callable 的方式來創(chuàng)建線程

  1. public class CallableDemo implements Callable<String> { 
  2.  
  3.     @Override 
  4.     public String call() throws Exception { 
  5.         int a=1; 
  6.         int b=2; 
  7.         System. out .println(a+b); 
  8.         return "執(zhí)行結(jié)果:"+(a+b); 
  9.     } 
  10.  
  11.     public static void main(String[] args) throws ExecutionException, InterruptedException { 
  12.         //創(chuàng)建一個可重用固定線程數(shù)為1的線程池 
  13.         ExecutorService executorService = Executors.newFixedThreadPool (1); 
  14.         CallableDemo callableDemo=new CallableDemo(); 
  15.         //執(zhí)行線程,用future來接收線程的返回值 
  16.         Future<String> future = executorService.submit(callableDemo); 
  17.         //打印線程的返回值 
  18.         System. out .println(future.get()); 
  19.         executorService.shutdown(); 
  20.     } 

執(zhí)行結(jié)果

  1. 執(zhí)行結(jié)果:3 

03、線程的生命周期

  1. NEW:初始狀態(tài),線程被構(gòu)建,但是還沒有調(diào)用 start 方法。
  2. RUNNABLED:運(yùn)行狀態(tài),JAVA 線程把操作系統(tǒng)中的就緒和運(yùn)行兩種狀態(tài)統(tǒng)一稱為“運(yùn)行中”。調(diào)用線程的 start() 方法使線程進(jìn)入就緒狀態(tài)。
  3. BLOCKED:阻塞狀態(tài),表示線程進(jìn)入等待狀態(tài),也就是線程因?yàn)槟撤N原因放棄了 CPU 使用權(quán)。比如訪問 synchronized 關(guān)鍵字修飾的方法,沒有獲得對象鎖。
  4. Waiting :等待狀態(tài),比如調(diào)用 wait() 方法。
  5. TIME_WAITING:超時等待狀態(tài),超時以后自動返回。比如調(diào)用 sleep(long millis) 方法
  6. TERMINATED:終止?fàn)顟B(tài),表示當(dāng)前線程執(zhí)行完畢。

看下源碼:

  1. public enum State { 
  2.         NEW, 
  3.         RUNNABLE, 
  4.         BLOCKED, 
  5.         WAITING, 
  6.         TIMED_WAITING, 
  7.         TERMINATED; 

04、線程的優(yōu)先級

  1. 線程的最小優(yōu)先級:1
  2. 線程的最大優(yōu)先級:10
  3. 線程的默認(rèn)優(yōu)先級:5
  4. 通過調(diào)用 getPriority() 和 setPriority(int newPriority) 方法來獲得和設(shè)置線程的優(yōu)先級

看下源碼:

  1. /** 
  2.      * The minimum priority that a thread can have. 
  3.      */ 
  4.     public final static int MIN_PRIORITY = 1; 
  5.  
  6.     /** 
  7.      * The default priority that is assigned to a thread. 
  8.      */ 
  9.     public final static int NORM_PRIORITY = 5; 
  10.  
  11.     /** 
  12.      * The maximum priority that a thread can have. 
  13.      */ 
  14.     public final static int MAX_PRIORITY = 10; 

看下代碼:

  1. public class ThreadA extends Thread { 
  2.  
  3.     public static void main(String[] args) { 
  4.         ThreadA a = new ThreadA(); 
  5.         System.out.println(a.getPriority());//5 
  6.         a.setPriority(8); 
  7.         System.out.println(a.getPriority());//8 
  8.     } 

線程優(yōu)先級特性:

  1. 繼承性:比如 A 線程啟動 B 線程,則B線程的優(yōu)先級與 A 是一樣的。
  2. 規(guī)則性:高優(yōu)先級的線程總是大部分先執(zhí)行完,但不代表高優(yōu)先級線程全部先執(zhí)行完。
  3. 隨機(jī)性:優(yōu)先級較高的線程不一定每一次都先執(zhí)行完。

05、線程的停止

  1. stop() 方法,這個方法已經(jīng)標(biāo)記為過時了,強(qiáng)制停止線程,相當(dāng)于 kill -9。
  2. interrupt() 方法,優(yōu)雅的停止線程。告訴線程可以停止了,至于線程什么時候停止,取決于線程自身。

看下停止線程的代碼:

  1. public class InterruptDemo { 
  2.     private static int i ; 
  3.     public static void main(String[] args) throws InterruptedException { 
  4.         Thread thread = new Thread(() -> { 
  5.             //默認(rèn)情況下isInterrupted 返回 false、通過 thread.interrupt 變成了 true 
  6.             while (!Thread.currentThread().isInterrupted()) { 
  7.                 i++; 
  8.             } 
  9.             System.out.println("Num:" + i); 
  10.         }, "interruptDemo"); 
  11.         thread.start(); 
  12.         TimeUnit.SECONDS.sleep(1); 
  13.         thread.interrupt(); //不加這句,thread線程不會停止 
  14.     } 

看上面這段代碼,主線程 main 方法調(diào)用 thread線程的 interrupt() 方法,就是告訴 thread 線程,你可以停止了(其實(shí)是將 thread 線程的一個屬性設(shè)置為了 true ),然后 thread 線程通過 isInterrupted() 方法獲取這個屬性來判斷是否設(shè)置為了 true。這里我再舉一個例子來說明一下,

看代碼:

  1. public class ThreadDemo { 
  2.     private volatile static Boolean interrupt = false ; 
  3.     private static int i ; 
  4.  
  5.     public static void main(String[] args) throws InterruptedException { 
  6.         Thread thread = new Thread(() -> { 
  7.             while (!interrupt) { 
  8.                 i++; 
  9.             } 
  10.             System.out.println("Num:" + i); 
  11.         }, "ThreadDemo"); 
  12.         thread.start(); 
  13.         TimeUnit.SECONDS.sleep(1); 
  14.         interrupt = true
  15.     } 

是不是很相似,再簡單總結(jié)一下:

當(dāng)其他線程通過調(diào)用當(dāng)前線程的 interrupt 方法,表示向當(dāng)前線程打個招呼,告訴他可以中斷線程的執(zhí)行了,并不會立即中斷線程,至于什么時候中斷,取決于當(dāng)前線程自己。

線程通過檢查自身是否被中斷來進(jìn)行相應(yīng),可以通過 isInterrupted() 來判斷是否被中斷。

這種通過標(biāo)識符來實(shí)現(xiàn)中斷操作的方式能夠使線程在終止時有機(jī)會去清理資源,而不是武斷地將線程停止,因此這種終止線程的做法顯得更加安全和優(yōu)雅。

06、線程的復(fù)位

兩種復(fù)位方式:

  1. Thread.interrupted()
  2. 通過拋出 InterruptedException 的方式

然后了解一下什么是復(fù)位:

線程運(yùn)行狀態(tài)時 Thread.isInterrupted() 返回的線程狀態(tài)是 false,然后調(diào)用 thread.interrupt() 中斷線程 Thread.isInterrupted() 返回的線程狀態(tài)是 true,最后調(diào)用 Thread.interrupted() 復(fù)位線程Thread.isInterrupted() 返回的線程狀態(tài)是 false 或者拋出 InterruptedException 異常之前,線程會將狀態(tài)設(shè)為 false。

下面來看下兩種方式復(fù)位線程的代碼,首先是 Thread.interrupted() 的方式復(fù)位代碼:

  1. public class InterruptDemo { 
  2.  
  3.     public static void main(String[] args) throws InterruptedException { 
  4.         Thread thread = new Thread(() -> { 
  5.             while (true) { 
  6.                 //Thread.currentThread().isInterrupted()默認(rèn)是false,當(dāng)main方式執(zhí)行thread.interrupt()時,狀態(tài)改為true 
  7.                 if (Thread.currentThread().isInterrupted()) { 
  8.                     System.out.println("before:" + Thread.currentThread().isInterrupted());//before:true 
  9.                     Thread.interrupted(); // 對線程進(jìn)行復(fù)位,由 true 變成 false 
  10.                     System.out.println("after:" + Thread.currentThread().isInterrupted());//after:false 
  11.                 } 
  12.             } 
  13.         }, "interruptDemo"); 
  14.         thread.start(); 
  15.         TimeUnit.SECONDS.sleep(1); 
  16.         thread.interrupt(); 
  17.     } 

拋出 InterruptedException 復(fù)位線程代碼:

  1. public class InterruptedExceptionDemo { 
  2.  
  3.     public static void main(String[] args) throws InterruptedException { 
  4.         Thread thread = new Thread(() -> { 
  5.             while (!Thread.currentThread().isInterrupted()) { 
  6.                 try { 
  7.                     TimeUnit.SECONDS.sleep(1); 
  8.                 } catch (InterruptedException e) { 
  9.                     e.printStackTrace(); 
  10.                     // break; 
  11.                 } 
  12.             } 
  13.         }, "interruptDemo"); 
  14.         thread.start(); 
  15.         TimeUnit.SECONDS.sleep(1); 
  16.         thread.interrupt(); 
  17.         System.out.println(thread.isInterrupted()); 
  18.     } 

結(jié)果:

  1. false 
  2. java.lang.InterruptedException: sleep interrupted 
  3.     at java.lang.Thread.sleep(Native Method) 
  4.     at java.lang.Thread.sleep(Thread.java:340) 
  5.     at java.util.concurrent.TimeUnit.sleep(TimeUnit.java:386) 
  6.     at com.cl.concurrentprogram.InterruptedExceptionDemo.lambda$main$0(InterruptedExceptionDemo.java:16) 
  7.     at java.lang.Thread.run(Thread.java:748) 

需要注意的是,InterruptedException 異常的拋出并不意味著線程必須終止,而是提醒當(dāng)前線程有中斷的操作發(fā)生,至于接下來怎么處理取決于線程本身,比如

  1. 直接捕獲異常不做任何處理
  2. 將異常往外拋出
  3. 停止當(dāng)前線程,并打印異常信息

像我上面的例子,如果拋出 InterruptedException 異常,我就break跳出循環(huán)讓 thread 線程終止。

為什么要復(fù)位:

Thread.interrupted() 是屬于當(dāng)前線程的,是當(dāng)前線程對外界中斷信號的一個響應(yīng),表示自己已經(jīng)得到了中斷信號,但不會立刻中斷自己,具體什么時候中斷由自己決定,讓外界知道在自身中斷前,他的中斷狀態(tài)仍然是 false,這就是復(fù)位的原因。

責(zé)任編輯:華軒 來源: Java極客技術(shù)
相關(guān)推薦

2017-09-19 14:53:37

Java并發(fā)編程并發(fā)代碼設(shè)計(jì)

2017-01-10 13:39:57

Python線程池進(jìn)程池

2023-07-03 09:59:00

并發(fā)編程并發(fā)容器

2020-12-08 08:53:53

編程ThreadPoolE線程池

2023-07-11 08:34:25

參數(shù)流程類型

2011-07-21 10:17:53

java

2012-03-09 10:44:11

Java

2025-02-17 00:00:25

Java并發(fā)編程

2025-02-19 00:05:18

Java并發(fā)編程

2011-12-29 13:31:15

Java

2025-06-18 08:10:00

Java并發(fā)編程開發(fā)

2021-03-10 15:59:39

JavaSynchronize并發(fā)編程

2023-04-02 17:53:10

多線程編程自測

2020-12-10 07:00:38

編程線程池定時任務(wù)

2020-12-04 19:28:53

CountDownLaPhaserCyclicBarri

2020-12-11 07:32:45

編程ThreadLocalJava

2020-11-13 08:42:24

Synchronize

2020-12-03 11:15:21

CyclicBarri

2020-11-30 16:01:03

Semaphore

2020-12-09 08:21:47

編程Exchanger工具
點(diǎn)贊
收藏

51CTO技術(shù)棧公眾號

主站蜘蛛池模板: 精品久久久久久18免费网站 | 亚洲福利 | 中文字幕在线国产 | 亚洲一区二区三区在线 | 91精品在线播放 | 国产精品日韩在线观看一区二区 | 91在线精品秘密一区二区 | 色天天综合| 久久久网 | 国产精品黄视频 | 免费观看www7722午夜电影 | 国产一区欧美一区 | 自拍视频网站 | 拍真实国产伦偷精品 | 国产一区二区在线免费观看 | 一区二区在线视频 | 1区2区3区视频 | 95国产精品 | 欧美精品在线一区 | 成人小视频在线观看 | 日韩第一区 | 一区二区日本 | 国产精品a级| 91国产精品 | 国产一级视屏 | 日韩黄色av | 久草视频在线播放 | 欧美国产免费 | 日韩精品免费视频 | 伊人伊人 | 亚洲欧美精品一区 | 国产一级久久久久 | 国产精品高清一区二区三区 | 91精品国产综合久久婷婷香蕉 | 精品国产乱码久久久久久丨区2区 | 中文字幕日韩一区 | 激情欧美一区二区三区 | 午夜看电影在线观看 | 色狠狠一区 | 国产精品久久久久久久久久久久午夜片 | 色婷婷婷婷色 |