日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

java Thread的start和run方法的区别

發(fā)布時間:2024/3/13 编程问答 43 豆豆
生活随笔 收集整理的這篇文章主要介紹了 java Thread的start和run方法的区别 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

一、認識Thread的 start() 和 run()

概述:

t.start()會導(dǎo)致run()方法被調(diào)用,run()方法中的內(nèi)容稱為線程體,它就是這個線程需要執(zhí)行的工作。

start()來啟動線程,實現(xiàn)了真正意義上的啟動線程,此時會出現(xiàn)異步執(zhí)行的效果,即在線程的創(chuàng)建和啟動中所述的隨機性。
而如果使用run()來啟動線程,就不是異步執(zhí)行了,而是同步執(zhí)行,不會達到使用線程的意義

1.start():

我們先來看看API中對于該方法的介紹:

“Causes this thread to begin execution; the Java Virtual Machine calls the run method of this thread.”?
“start()方法會使得該線程開始執(zhí)行;java虛擬機會去調(diào)用該線程的run()方法?!?/p>

???? 使該線程開始執(zhí)行;Java 虛擬機調(diào)用該線程的?run?方法。

???? 結(jié)果是兩個線程并發(fā)地運行;當(dāng)前線程(從調(diào)用返回給?start?方法)和另一個線程(執(zhí)行其?run?方法)。

???? 多次啟動一個線程是非法的。特別是當(dāng)線程已經(jīng)結(jié)束執(zhí)行后,不能再重新啟動。

用start方法來啟動線程,真正實現(xiàn)了多線程運行,這時無需等待run方法體代碼執(zhí)行完畢而直接繼續(xù)執(zhí)行下面的代碼。通過調(diào)

用Thread類的 start()方法來啟動一個線程,這時此線程處于就緒(可運行)狀態(tài),并沒有運行,一旦得到cpu時間片,就開始

執(zhí)行run()方法,這里方法 run()稱為線程體,它包含了要執(zhí)行的這個線程的內(nèi)容,Run方法運行結(jié)束,此線程隨即終止。

?

2.run():

public class Thread extends Object implements Runnable

我們還是先看看API中對該方法的介紹:

????? 如果該線程是使用獨立的?Runnable?運行對象構(gòu)造的,則調(diào)用該?Runnable?對象的?run?方法;否則,該方法不執(zhí)行任何操作并返回。

??? Thread?的子類應(yīng)該重寫該方法。

run()方法只是類的一個普通方法而已,如果直接調(diào)用Run方法,程序中依然只有主線程這一個線程,其程序執(zhí)行路徑還是只有

一條,還是要順序執(zhí)行,還是要等待run方法體執(zhí)行完畢后才可繼續(xù)執(zhí)行下面的代碼,這樣就沒有達到寫線程的目的。

?

3.總結(jié)

調(diào)用start方法方可啟動線程,而run方法只是thread的一個普通方法調(diào)用,還是在主線程里執(zhí)行。

二、代碼實例:

?通過start啟動線程,異步啟動

public?static?void?main(String args[]) {Thread t = new?Thread() {public?void?run() {pong();}};t.start();System.out.print("ping");}static?void?pong() {System.out.print("pong");}

輸出結(jié)果: pingpong

?

通過run啟動線程,同步啟動

public?static?void?main(String args[]) {Thread t = new?Thread() {public?void?run() {pong();}};t.run();System.out.print("ping");}static?void?pong() {System.out.print("pong");}

輸出結(jié)果:pongping

?

通過以上兩個程序?qū)嵗?#xff0c;可以很容易的區(qū)分出start()方法和run()方法的區(qū)別:

t.start(); 該行代碼相當(dāng)于是啟動線程,異步操作

t.run(); 該行代碼相當(dāng)于是使用t這個類中的run方法而已,只是主線程的一個普通的方法

三、線程狀態(tài)說明:

線程狀態(tài)從大的方面來說,可歸結(jié)為:初始狀態(tài)、可運行狀態(tài)、不可運行狀態(tài)消亡狀態(tài),說明如下:

1)線程的實現(xiàn)有兩種方式,一是繼承Thread類,二是實現(xiàn)Runnable接口,但不管怎樣,當(dāng)我們new了thread實例后,線程就進入了初始狀態(tài);

2)當(dāng)該對象調(diào)用了start()方法,就進入可運行狀態(tài);

3)進入可運行狀態(tài)后,當(dāng)該對象被操作系統(tǒng)選中,獲得CPU時間片就會進入運行狀態(tài);

4)進入運行狀態(tài)后情況就比較多,大致有如下情形:

? ? ? ?a.?run()方法或main()方法結(jié)束后,線程就進入終止?fàn)顟B(tài);

? ? ? ?b. 當(dāng)線程調(diào)用了自身的sleep()方法其他線程的join()方法,就會進入阻塞狀態(tài)(該狀態(tài)既停止當(dāng)前線程,但并不釋放

所占有的資源)。當(dāng)sleep()結(jié)束或join()結(jié)束后,該線程進入可運行狀態(tài),繼續(xù)等待OS分配時間片; 當(dāng)線程剛進入可運行

狀態(tài)(注意,還沒運行),發(fā)現(xiàn)將要調(diào)用的資源被鎖牢(synchroniza,lock),將會立即進入鎖池狀態(tài),等待獲取鎖標(biāo)記(這時

的鎖池里也許已經(jīng)有了其他線程在等待獲取鎖標(biāo)記,這時它們處于隊列狀態(tài),既先到先得),一旦線程獲得鎖標(biāo)記后,就

轉(zhuǎn)入可運行狀態(tài),等待OS分配 CPU時間片;

? ? ? ? c. 當(dāng)線程調(diào)用wait()方法后會進入等待隊列(進入這個狀態(tài)會釋放所占有的所有資源,與阻塞狀態(tài)不同),進入這個狀

態(tài)后,是不能自動喚醒的,必須依靠其他線程調(diào)用notify()或notifyAll()方法才能被喚醒(由于notify()只是喚醒一個線程,

但我們由不能確定具體喚醒的是哪一個線程,也許我們需要喚醒的線程不能夠被喚醒,因此在實際使用時,一般都用

notifyAll()方法,喚醒有所線程),線程被喚醒后會進入鎖池,等待獲取鎖標(biāo)記。 當(dāng)線程調(diào)用stop方法,即可使線程進入消

亡狀態(tài),但是由于stop方法是不安全的,不鼓勵使用,大家可以通過run方法里的條件變通實現(xiàn)線程的 stop。

總結(jié)

以上是生活随笔為你收集整理的java Thread的start和run方法的区别的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。