偷偷摘套内射激情视频,久久精品99国产国产精,中文字幕无线乱码人妻,中文在线中文a,性爽19p

妹子問我為啥啟動線程時使用 Start 而不是 Run

網(wǎng)絡 通信技術(shù)
今天團隊里面的妹子問阿粉,為什么在啟動線程的時候,都使用 start 方法,而不是 run 方法呢?

[[357639]]

 本文轉(zhuǎn)載自微信公眾號「Java極客技術(shù)」,作者鴨血粉絲。轉(zhuǎn)載本文請聯(lián)系Java極客技術(shù)公眾號。   

今天團隊里面的妹子問阿粉,為什么在啟動線程的時候,都使用 start 方法,而不是 run 方法呢

還好阿粉平時一直有在學習,要不真的被妹子問住了

在多線程中,如果想讓一個線程啟動,你使用的方法一定是 thread.start() 方法,而不是 thread.run() 方法(啥,你用的不是 thread.start() 方法?乖,你的打開方式不對哦,下次不要這樣了

有沒有疑惑,為什么每次我們都習慣調(diào)用 start() 方法,為什么不直接調(diào)用 run() 方法來啟動線程呢?

而且如果去看源碼的話,你會發(fā)現(xiàn),在 thread.start() 方法中,其實最后還是調(diào)用了 thread.run() 方法來執(zhí)行

  1. Causes this thread to begin execution; the Java Virtual Machine 
  2.  calls the <code>run</code> method of this thread. 

上面的注釋翻譯一下:當線程開始執(zhí)行時, JVM 會調(diào)用此線程的 run 方法

也就是說,線程的 run 方法是由 JVM 直接調(diào)用的,在 Java 中如果我們想要直接調(diào)用 run 方法也是可以的,因為在 Java 中 run 方法是 public 的

  1. @Override 
  2.    public void run() { 
  3.        if (target != null) { 
  4.            target.run(); 
  5.        } 
  6.    } 

那既然 start 方法最后調(diào)用的也是 run 方法,再加上 run 方法本身支持直接調(diào)用,那為啥我們平時寫的程序都是調(diào)用 start 方法,而不是 run 方法呢

那是因為,如果直接調(diào)用 run 方法,就不是多線程了

為了方便解釋,咱們看個小 demo :

  1. public class RunThread { 
  2.     public static void main(String[] args) { 
  3.         Thread runThread = new Thread(new Runnable() { 
  4.             @Override 
  5.             public void run() { 
  6.                 System.out.printf("Run begin another , 當前線程 : %s.%n" ,Thread.currentThread().getName()); 
  7.             } 
  8.         }); 
  9.  
  10.         // 啟動線程 
  11.         runThread.start(); 
  12.  
  13.         // 直接調(diào)用 run 方法 -- 演示使用,實際中不要這么做! 
  14.         runThread.run(); 
  15.  
  16.         System.out.printf("Run begin , 當前線程 : %s.%n" ,Thread.currentThread().getName()); 
  17.     } 

上面的程序運行結(jié)果如下:

你會發(fā)現(xiàn), runThread 的 run 方法被執(zhí)行了兩次

一次是 run 方法運行在自己的線程中,從 Run begin another , 當前線程 : Thread-0 可以看到,這個線程是運行在 Thread-0 中

另外一次是因為我們的程序代碼直接調(diào)用了 run 方法,此時的線程運行在 main 線程中,從 Run begin another , 當前線程 : main 可以看出來

也就是說,如果我們直接調(diào)用 run 方法的話,線程并不是運行在自己的線程中,而是運行在了當前線程中

我們?yōu)槭裁匆獎?chuàng)建多線程?不就是希望多個線程并行執(zhí)行,比如現(xiàn)在我是線程 A ,此時又起了一個線程,那么我希望這個線程是和線程 A 一起運行的,如果直接調(diào)用了 run 方法的話,就運行在線程 A 里面來了

并沒有達到創(chuàng)建多線程的目標,這怎么行呢,對不對

所以在啟動線程時,都是使用 start 方法,而不是 run 方法

這一點,其實在源碼中也有說明:

the Java Virtual Machine calls the run method of this thread.

The result is that two threads are running concurrently:

the current thread (which returns from the call to the start method)

and the other thread (which executes its run method).

在 JVM 調(diào)用線程的 run 方法之后,結(jié)果就是兩個線程同時運行:

  • 當前線程(從調(diào)用返回到 start 方法)
  • 另一個線程(執(zhí)行 run 方法)

一個線程能不能 start 兩次?

妹子搞懂了為什么線程一般都使用 start 方法,不使用 run 方法,因為調(diào)用的話,就違背了我們想要用多線程去處理的初衷

妹子又問阿粉,那一個線程是不是可以 start 兩次呢?

負責任的阿粉趕緊告訴小妹妹是不可以的

如果一個線程啟動兩次,想都不用想會拋出 IllegalThreadStateException 這個異常

這個錯誤我們也能在源碼中看到:

  1. if (threadStatus != 0) 
  2.     throw new IllegalThreadStateException(); 

線程開始 start 時,會首先判斷 threadStatus 的值是否為 0 ,如果值不是 0 的話,說明這個線程的 state 狀態(tài)不是 new 就拋出 IllegalThreadStateException 異常

啊?竟然還想問阿粉,線程的狀態(tài)除了 new 還有什么?阿粉以前寫過一篇,要不要看看:面試官沒想到,一個 Java 線程生命周期,我可以扯半小時

 

責任編輯:武曉燕 來源: Java極客技術(shù)
相關(guān)推薦

2020-05-12 08:56:16

Java 線程開發(fā)

2024-08-01 10:10:24

MySQL場景搜索

2022-09-05 15:36:47

線程方法Java

2022-02-15 07:03:04

start 源碼run線程

2019-08-28 12:31:31

戴爾

2020-10-26 07:07:50

線程安全框架

2013-03-25 10:14:18

NginxApache

2023-03-29 09:01:46

HSBRGB模型

2020-11-26 10:58:08

線程啟動

2020-07-24 09:20:44

MapObject前端

2020-09-15 09:23:19

C++WindowsC#

2021-03-26 11:50:28

Linuxexals

2023-03-01 10:42:58

gRPC服務端設(shè)置

2021-06-30 12:47:12

標簽HTML分辨率

2021-02-26 05:30:25

元素For-Each代碼

2024-02-20 20:12:09

C語言字符串Redis

2022-05-09 19:59:15

RedisLRU 算法

2022-05-02 17:34:25

大數(shù)據(jù)數(shù)據(jù)分析

2022-12-02 14:00:55

CIO交付能力

2023-06-14 16:40:31

LinuxWSL
點贊
收藏

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