java多線程課件資料_第1頁(yè)
java多線程課件資料_第2頁(yè)
java多線程課件資料_第3頁(yè)
java多線程課件資料_第4頁(yè)
java多線程課件資料_第5頁(yè)
已閱讀5頁(yè),還剩39頁(yè)未讀 繼續(xù)免費(fèi)閱讀

下載本文檔

版權(quán)說(shuō)明:本文檔由用戶(hù)提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請(qǐng)進(jìn)行舉報(bào)或認(rèn)領(lǐng)

文檔簡(jiǎn)介

1、Java中的多線程為什么會(huì)有多線程?多任務(wù)分時(shí)操作系統(tǒng)的出現(xiàn)(windows,linux)什么是分時(shí)操作系統(tǒng)可以同一時(shí)間執(zhí)行多個(gè)程序的操作系統(tǒng),用戶(hù)邊上網(wǎng),邊聽(tīng)歌操作系統(tǒng)為什么能同時(shí)執(zhí)行多個(gè)任務(wù)?CPU同時(shí)執(zhí)行多個(gè)程序?CPU只是將時(shí)間切割為時(shí)間片,然后將時(shí)間片分配給這些程序,獲得時(shí)間片的程序開(kāi)始執(zhí)行,不等執(zhí)行完畢,下個(gè)程序又獲得時(shí)間片開(kāi)始執(zhí)行,這樣多個(gè)程序輪流執(zhí)行一段時(shí)間,由于現(xiàn)在cpu的高速計(jì)算能力,給人的感覺(jué)就像是多個(gè)程序在同時(shí)執(zhí)行一樣。多線程的概念進(jìn)程的概念一個(gè)進(jìn)程就是一個(gè)執(zhí)行中的程序,每一個(gè)進(jìn)程都有自己獨(dú)立的一塊內(nèi)存空間,一組系統(tǒng)資源進(jìn)程的特點(diǎn)每一個(gè)進(jìn)程的內(nèi)部數(shù)據(jù)和狀態(tài)都是完全獨(dú)立的

2、.因此可以想像創(chuàng)建并執(zhí)行一個(gè)進(jìn)程的系統(tǒng)開(kāi)銷(xiāo)是比較大的 多任務(wù)多任務(wù)是指在一個(gè)系統(tǒng)中可以同時(shí)運(yùn)行多個(gè)程序,即有多個(gè)獨(dú)立運(yùn)行的任務(wù),每個(gè)任務(wù)對(duì)應(yīng)一個(gè)進(jìn)程 多線程的概念線程的概念線程與進(jìn)程相似,是一段完成某個(gè)特定功能的代碼,是程序中單個(gè)順序的流控制,在java中,程序通過(guò)流控制來(lái)執(zhí)行程序流,程序中單個(gè)順序的流控制稱(chēng)為線程什么是多線程多線程則指的是在單個(gè)程序中可以同時(shí)運(yùn)行多個(gè)不同的線程,執(zhí)行不同的任務(wù).多線程意味著一個(gè)程序的多行語(yǔ)句可以看上去幾乎在同一時(shí)間內(nèi)同時(shí)運(yùn)行 多線程的概念進(jìn)程與線程的區(qū)別進(jìn)程都有自己獨(dú)立的一塊內(nèi)存空間,一組系統(tǒng)資源。線程是共享一塊內(nèi)存空間和一組系統(tǒng)資源,系統(tǒng)在產(chǎn)生一個(gè)線程,或者

3、在各個(gè)線程之間切換時(shí),負(fù)擔(dān)要比進(jìn)程小的多 。線程也被稱(chēng)為輕負(fù)荷進(jìn)程(light-weight process)一個(gè)進(jìn)程中可以包含多個(gè)線程,線程總是屬于某個(gè)進(jìn)程,進(jìn)程中的多個(gè)線程共享進(jìn)程的內(nèi)存。 多線程的概念一個(gè)線程實(shí)例只是一個(gè)對(duì)象,像Java中的任何其他對(duì)象一樣,具有變量和方法,生死于堆上一個(gè)Java應(yīng)用總是從main()方法開(kāi)始運(yùn)行,main()方法運(yùn)行在一個(gè)線程內(nèi),它被稱(chēng)為主線程。Java中創(chuàng)建線程繼承java.lang.Thread類(lèi)實(shí)現(xiàn)java.lang.Runnable接口Java中的線程繼承Java.lang.Thread繼承Thread覆蓋Thread的run()方法,將你要讓線

4、程做的事寫(xiě)在run方法中。有時(shí)候可以需要用循環(huán),使你的代碼一直執(zhí)行下去New 這個(gè)Thead子類(lèi),得到一個(gè)對(duì)象調(diào)用這個(gè)對(duì)象的start()方法。線程被啟動(dòng),開(kāi)始執(zhí)行run()中的代碼。Java中的線程例子這個(gè)例子實(shí)現(xiàn)一個(gè)定時(shí)線程,即線程在給定期間每隔一定時(shí)間(1秒),屏幕顯示時(shí)間累計(jì)數(shù)(秒數(shù)),時(shí)間結(jié)束時(shí)線程自動(dòng)停止、撤消。Java中的線程演示示例:繼承Thread實(shí)現(xiàn)java.lang.Runnable接口由于繼承了Thread后,類(lèi)再不能繼承別的類(lèi),所以一般我們采用實(shí)現(xiàn)Runnable接口的方法來(lái)創(chuàng)建線程提供一個(gè)實(shí)現(xiàn)接口Runnable的類(lèi),實(shí)現(xiàn)run()方法。得到這個(gè)類(lèi)的實(shí)例A。New

5、一個(gè)Thread對(duì)象,同時(shí)A作為參數(shù)傳入。例如:Thread runner=new Thread(A);調(diào)用start啟動(dòng)線程。例如:runner.start();Java中的線程例子這個(gè)例子與剛才哪個(gè)例子不同點(diǎn)在于要實(shí)現(xiàn)Runable接口,必須實(shí)現(xiàn)run()方法,否則將不能通過(guò)編譯。而繼承Thread類(lèi)的線程機(jī)制則不一定要重載其run( )方法,線程類(lèi)將自動(dòng)調(diào)用其基類(lèi)的run( )方法Java中的線程演示示例:實(shí)現(xiàn)Runnable接口線程的機(jī)制圖 Java中的狀態(tài)線程的狀態(tài)表示線程正在進(jìn)行的活動(dòng)以及在此時(shí)間段內(nèi)所能完成的任務(wù).線程有創(chuàng)建,可運(yùn)行,運(yùn)行中,阻塞,死亡五種狀態(tài).一個(gè)具有生命的線程

6、,總是處于這五種狀態(tài)之一:創(chuàng)建狀態(tài):線程對(duì)象已經(jīng)創(chuàng)建,還沒(méi)有在其上調(diào)用start()方法。(new thread)可運(yùn)行狀態(tài):使用start()方法啟動(dòng)一個(gè)線程后,系統(tǒng)為該線程分配了除CPU外的所需資源,使該線程處于可運(yùn)行狀態(tài) 。(Runnable)運(yùn)行中狀態(tài):JVM調(diào)度選中一個(gè)Runnable的線程,使其占有CPU并轉(zhuǎn)為運(yùn)行中狀態(tài)(Running).此時(shí),系統(tǒng)真正執(zhí)行線程的run()方法.Java中的狀態(tài)等待/阻塞/睡眠狀態(tài):這是線程有資格運(yùn)行時(shí)它所處的狀態(tài)。實(shí)際上這個(gè)三狀態(tài)組合為一種,其共同點(diǎn)是:線程仍舊是活的,但是當(dāng)前沒(méi)有條件運(yùn)行。換句話說(shuō),它是可運(yùn)行的,但是如果某件事件出現(xiàn),他可能返回

7、到可運(yùn)行狀態(tài)。死亡態(tài):當(dāng)線程的run()方法完成時(shí)就認(rèn)為它死去。這個(gè)線程對(duì)象也許是活的,但是,它已經(jīng)不是一個(gè)單獨(dú)執(zhí)行的線程。線程一旦死亡,就不能復(fù)生。 如果在一個(gè)死去的線程上調(diào)用start()方法,會(huì)拋出java.lang.IllegalThreadStateException異常。 Java中的狀態(tài)Java中的多線程java中多線程就是一個(gè)類(lèi)或一個(gè)程序執(zhí)行或管理多個(gè)線程執(zhí)行任務(wù)的能力,每個(gè)線程可以獨(dú)立于其他線程而獨(dú)立運(yùn)行,當(dāng)然也可以和其他線程協(xié)同運(yùn)行,一個(gè)類(lèi)控制著它的所有線程,可以決定哪個(gè)線程得到優(yōu)先級(jí),哪個(gè)線程可以訪問(wèn)其他類(lèi)的資源,哪個(gè)線程開(kāi)始執(zhí)行,哪個(gè)保持休眠狀態(tài)。Java中的多線程線程

8、的執(zhí)行機(jī)制同一時(shí)刻如果有多個(gè)線程處于可運(yùn)行狀態(tài),則他們需要排隊(duì)等待CPU資源.此時(shí)每個(gè)線程自動(dòng)獲得一個(gè)線程的優(yōu)先級(jí)(priority),優(yōu)先級(jí)的高低反映線程的重要或緊急程度.可運(yùn)行狀態(tài)的線程按優(yōu)先級(jí)排隊(duì),線程調(diào)度依據(jù)優(yōu)先級(jí)基礎(chǔ)上的“先到先服務(wù)”原則 。線程調(diào)度管理器負(fù)責(zé)線程排隊(duì)和CPU在線程序的分配,并由線程調(diào)度算法進(jìn)行調(diào)度.當(dāng)線程調(diào)度管理器選種某個(gè)線程時(shí),該線程獲得CPU資源而進(jìn)入運(yùn)行狀態(tài).線程調(diào)度是先占式調(diào)度,即如果在當(dāng)前線程執(zhí)行過(guò)程中一個(gè)更高優(yōu)先級(jí)的線程進(jìn)入可運(yùn)行狀態(tài),則這個(gè)線程立即被調(diào)度執(zhí)行.先占式調(diào)度分為:獨(dú)占式和分時(shí)方式.Java中的線程機(jī)制獨(dú)占式獨(dú)占方式下,當(dāng)前執(zhí)行線程將一直執(zhí)行

9、下去,直到執(zhí)行完或由于某種原因主動(dòng)放棄CPU,或CPU被一個(gè)更高優(yōu)先級(jí)的線程搶占分時(shí)方式 分時(shí)方式下,當(dāng)前運(yùn)行線程獲得一個(gè)時(shí)間片,時(shí)間到時(shí),即使沒(méi)有執(zhí)行完也要讓出CPU,進(jìn)入可運(yùn)行狀態(tài),等待下一個(gè)時(shí)間片的調(diào)度.系統(tǒng)選中其他可運(yùn)行狀態(tài)的線程執(zhí)行分時(shí)方式的系統(tǒng)使每個(gè)線程工作若干步,實(shí)現(xiàn)多線程同時(shí)運(yùn)行Java中的線程機(jī)制線程的執(zhí)行機(jī)制那么會(huì)打印出:My Name is Thread-0My Name is Thread-1My Name is Thread-2看了上面的結(jié)果,你可能會(huì)認(rèn)為線程的執(zhí)行順序是依次執(zhí)行的,但是那只是一般情況,千萬(wàn)不要以為這是線程的執(zhí)行機(jī)制;影響線程執(zhí)行順序的因素有幾點(diǎn)Jav

10、a中的線程執(zhí)行機(jī)制演示示例:線程的執(zhí)行機(jī)制首先看看前面提到的優(yōu)先級(jí)別再看看結(jié)果:My Name is Thread-1My Name is Thread-0My Name is Thread-2線程的優(yōu)先級(jí)分為10級(jí),分別用1到10的整數(shù)代表線程默認(rèn)優(yōu)先級(jí)是5,Thread類(lèi)中有三個(gè)常量,定義線程優(yōu)先級(jí)范圍:static int MAX_PRIORITY 線程可以具有的最高優(yōu)先級(jí)。 static int MIN_PRIORITY 線程可以具有的最低優(yōu)先級(jí)。 static int NORM_PRIORITY 分配給線程的默認(rèn)優(yōu)先級(jí)。 Java中的線程執(zhí)行機(jī)制演示示例:線程的執(zhí)行機(jī)制2其次是線程程

11、序本身的設(shè)計(jì),比如使用sleep,yield,join,wait等方法(詳情請(qǐng)看JDKDocument)Thread.sleep(longmillis );執(zhí)行后觀察其輸出:Thread-0 睡了 13Thread-2 睡了 92Thread-1 睡了 94上面的執(zhí)行結(jié)果是隨機(jī)的,再執(zhí)行很可能出現(xiàn)不同的結(jié)果。由于上面在run中添加了休眠語(yǔ)句,當(dāng)線程休眠的時(shí)候就會(huì)讓出cpu,cpu將會(huì)選擇執(zhí)行處于runnable狀態(tài)中的其他線程,當(dāng)然也可能出現(xiàn)這種情況,休眠的Thread立即進(jìn)入了runnable狀態(tài),cpu再次執(zhí)行它。Java中的線程執(zhí)行機(jī)制演示示例:線程的執(zhí)行機(jī)制3注意:線程睡眠是幫助其它線

12、程獲得運(yùn)行機(jī)會(huì)的最好方法。線程睡眠到期自動(dòng)蘇醒,并返回到可運(yùn)行狀態(tài),不是運(yùn)行狀態(tài)。sleep()中指定的時(shí)間是線程不會(huì)運(yùn)行的最短時(shí)間。因此,sleep()方法不能保證該線程睡眠到期后就開(kāi)始執(zhí)行。sleep()是靜態(tài)方法,只能控制當(dāng)前正在運(yùn)行的線程。Java中的線程執(zhí)行機(jī)制Thread.yield()方法 Thread.yield()靜態(tài)方法作用是:暫停當(dāng)前正在執(zhí)行的線程對(duì)象,并執(zhí)行其他線程。yield()應(yīng)該做的是讓當(dāng)前運(yùn)行線程回到可運(yùn)行狀態(tài),以允許具有相同優(yōu)先級(jí)的其他線程獲得運(yùn)行機(jī)會(huì)。因此,使用yield()的目的是讓相同優(yōu)先級(jí)的線程之間能適當(dāng)?shù)妮嗈D(zhuǎn)執(zhí)行。但是,實(shí)際中無(wú)法保證yield()達(dá)

13、到讓步目的,因?yàn)樽尣降木€程還有可能被線程調(diào)度程序再次選中。結(jié)論:yield()從未導(dǎo)致線程轉(zhuǎn)到等待/睡眠/阻塞狀態(tài)。在大多數(shù)情況下,yield()將導(dǎo)致線程從運(yùn)行狀態(tài)轉(zhuǎn)到可運(yùn)行狀態(tài),但有可能沒(méi)有效果。Java中的線程執(zhí)行機(jī)制演示示例:執(zhí)行yield()方法執(zhí)行結(jié)果:線程2第0次執(zhí)行!線程1第0次執(zhí)行!線程1第1次執(zhí)行!線程1第2次執(zhí)行!線程1第3次執(zhí)行!線程1第4次執(zhí)行!線程1第5次執(zhí)行!線程1第6次執(zhí)行!線程1第7次執(zhí)行!線程1第8次執(zhí)行!線程1第9次執(zhí)行!線程2第1次執(zhí)行!線程2第2次執(zhí)行!線程2第3次執(zhí)行!線程2第4次執(zhí)行!線程2第5次執(zhí)行!線程2第6次執(zhí)行!線程2第7次執(zhí)行!線程2第8

14、次執(zhí)行!線程2第9次執(zhí)行!Java中的線程執(zhí)行機(jī)制Thread.join()方法將幾個(gè)并行線程合并為一個(gè)單線程執(zhí)行,應(yīng)用場(chǎng)景是當(dāng)一個(gè)線程必須等待另一個(gè)線程執(zhí)行完畢才能執(zhí)行時(shí)可以使用join方法。 join為非靜態(tài)方法,定義如下:void join()等待該線程終止。Java中的線程執(zhí)行機(jī)制演示示例:執(zhí)行Join()方法執(zhí)行結(jié)果:主線程第0次執(zhí)行!線程1第0次執(zhí)行!主線程第1次執(zhí)行!主線程第2次執(zhí)行!主線程第3次執(zhí)行!線程1第1次執(zhí)行!線程1第2次執(zhí)行!線程1第3次執(zhí)行!線程1第4次執(zhí)行!線程1第5次執(zhí)行!線程1第6次執(zhí)行!線程1第7次執(zhí)行!線程1第8次執(zhí)行!線程1第9次執(zhí)行!主線程第4次執(zhí)行!

15、主線程第5次執(zhí)行!主線程第6次執(zhí)行!主線程第7次執(zhí)行!主線程第8次執(zhí)行!主線程第9次執(zhí)行!主線程第10次執(zhí)行!主線程第11次執(zhí)行!Java中的線程執(zhí)行機(jī)制同步的提出:線程的同步是為了防止多個(gè)線程訪問(wèn)一個(gè)數(shù)據(jù)對(duì)象時(shí),對(duì)數(shù)據(jù)造成的破壞。例如:兩個(gè)線程ThreadA、ThreadB都操作同一個(gè)對(duì)象Foo對(duì)象,并修改Foo對(duì)象上的數(shù)據(jù)。線程的同步與鎖演示示例:兩個(gè)線程同時(shí)操作同一個(gè)對(duì)象運(yùn)行結(jié)果:Thread-A : 當(dāng)前foo對(duì)象的x值= 40Thread-B : 當(dāng)前foo對(duì)象的x值= 40Thread-A : 當(dāng)前foo對(duì)象的x值= -20Thread-B : 當(dāng)前foo對(duì)象的x值= -20Thr

16、ead-B : 當(dāng)前foo對(duì)象的x值= -80Thread-A : 當(dāng)前foo對(duì)象的x值= -80從結(jié)果發(fā)現(xiàn),這樣的輸出值明顯是不合理的。原因是兩個(gè)線程不加控制的訪問(wèn)Foo對(duì)象并修改其數(shù)據(jù)所致。如果要保持結(jié)果的合理性,需要對(duì)Foo的訪問(wèn)加以限制,每次只能有一個(gè)線程在訪問(wèn)。這樣就能保證Foo對(duì)象中數(shù)據(jù)的合理性了。線程的同步與鎖使用同步鎖synchronized關(guān)鍵字同步方法或代碼語(yǔ)法:synchronized 可以修飾代碼塊,在使用同步代碼塊時(shí)候,應(yīng)該指定在哪個(gè)對(duì)象上同步,也就是說(shuō)要獲取哪個(gè)對(duì)象的鎖例如:public int fix(int y) synchronized (this) x =

17、x - y; return x;線程的同步與鎖接上 synchronized也可以作為一個(gè)method的修飾符非靜態(tài)方法public synchronized int getX() return x+;等價(jià)于public int getX() synchronized(this)return x+;線程的同步與鎖接上要同步靜態(tài)方法,需要一個(gè)用于整個(gè)類(lèi)對(duì)象的鎖,這個(gè)對(duì)象是就是這個(gè)類(lèi)(XXX.class)對(duì)象。例如:public static synchronized int setName(String name) X = name;等價(jià)于public static int set

18、Name(String name) synchronized(Xxx.class) X = name; 線程的同步與鎖注意:synchronized只能標(biāo)記非抽象的方法,不能標(biāo)識(shí)成員變量Java中每個(gè)對(duì)象都有一個(gè)內(nèi)置鎖當(dāng)程序運(yùn)行到非靜態(tài)的synchronized同步方法上時(shí),自動(dòng)獲得與正在執(zhí)行代碼類(lèi)的當(dāng)前實(shí)例(this實(shí)例)有關(guān)的鎖當(dāng)程序運(yùn)行到synchronized同步方法或代碼塊時(shí)該對(duì)象鎖才起作用一個(gè)對(duì)象只有一個(gè)鎖。所以,如果一個(gè)線程獲得該鎖,就沒(méi)有其他線程可以獲得鎖,直到第一個(gè)線程釋放(或返回)鎖。這也意味著任何其他線程都不能進(jìn)入該對(duì)象上的synchronized方法或代碼

19、塊,直到該鎖被釋放釋放鎖是指持鎖線程退出了synchronized同步方法或代碼塊線程的同步與鎖線程同步的運(yùn)用運(yùn)行結(jié)果:線程C運(yùn)行結(jié)束,增加“-80”,當(dāng)前用戶(hù)賬戶(hù)余額為:20線程D運(yùn)行結(jié)束,增加“-30”,當(dāng)前用戶(hù)賬戶(hù)余額為:-10線程E運(yùn)行結(jié)束,增加“32”,當(dāng)前用戶(hù)賬戶(hù)余額為:22線程F運(yùn)行結(jié)束,增加“21”,當(dāng)前用戶(hù)賬戶(hù)余額為:43線程B運(yùn)行結(jié)束,增加“-60”,當(dāng)前用戶(hù)賬戶(hù)余額為:-17線程A運(yùn)行結(jié)束,增加“20”,當(dāng)前用戶(hù)賬戶(hù)余額為:3線程的同步與鎖演示示例:多個(gè)線程同時(shí)操作同一個(gè)對(duì)象線程同步的運(yùn)用如果把上例子方法中的synchronized去掉運(yùn)行結(jié)果:線程B運(yùn)行結(jié)束,增加“-6

20、0”,當(dāng)前用戶(hù)賬戶(hù)余額為:-29線程F運(yùn)行結(jié)束,增加“21”,當(dāng)前用戶(hù)賬戶(hù)余額為:3線程A運(yùn)行結(jié)束,增加“20”,當(dāng)前用戶(hù)賬戶(hù)余額為:-29線程C運(yùn)行結(jié)束,增加“-80”,當(dāng)前用戶(hù)賬戶(hù)余額為:3線程E運(yùn)行結(jié)束,增加“32”,當(dāng)前用戶(hù)賬戶(hù)余額為:3線程D運(yùn)行結(jié)束,增加“-30”,當(dāng)前用戶(hù)賬戶(hù)余額為:3 原因:多個(gè)線程并發(fā)訪問(wèn)了競(jìng)爭(zhēng)資源u,并對(duì)u的屬性做了改動(dòng)。線程的同步與鎖同步鎖要點(diǎn):只能同步方法,而不能同步變量和類(lèi);每個(gè)對(duì)象只有一個(gè)鎖;當(dāng)提到同步時(shí),應(yīng)該清楚在什么上同步?也就是說(shuō),在哪個(gè)對(duì)象上同步不必同步類(lèi)中所有的方法,類(lèi)可以同時(shí)擁有同步和非同步方法。如果兩個(gè)線程要執(zhí)行一個(gè)類(lèi)中的synchro

21、nized方法,并且兩個(gè)線程使用相同的實(shí)例來(lái)調(diào)用方法,那么一次只能有一個(gè)線程能夠執(zhí)行方法,另一個(gè)需要等待,直到鎖被釋放。也就是說(shuō):如果一個(gè)線程在對(duì)象上獲得一個(gè)鎖,就沒(méi)有任何其他線程可以進(jìn)入(該對(duì)象的)類(lèi)中的任何一個(gè)同步方法。線程的同步與鎖接上:如果線程擁有同步和非同步方法,則非同步方法可以被多個(gè)線程自由訪問(wèn)而不受鎖的限制。線程睡眠時(shí),它所持的任何鎖都不會(huì)釋放。 線程可以獲得多個(gè)鎖。比如,在一個(gè)對(duì)象的同步方法里面調(diào)用另外一個(gè)對(duì)象的同步方法,則獲取了兩個(gè)對(duì)象的同步鎖。同步損害并發(fā)性,應(yīng)該盡可能縮小同步范圍。線程的同步與鎖線程不能獲得鎖會(huì)怎么樣如果線程試圖進(jìn)入同步方法,而其鎖已經(jīng)被占用,則線程在該對(duì)

22、象上被阻塞。實(shí)質(zhì)上,線程進(jìn)入該對(duì)象的的一種池中,必須在那里等待,直到其鎖被釋放,該線程再次變?yōu)榭蛇\(yùn)行或運(yùn)行。當(dāng)考慮阻塞時(shí),一定要注意哪個(gè)對(duì)象正被用于鎖定:調(diào)用同一個(gè)對(duì)象中非靜態(tài)同步方法的線程將彼此阻塞。如果是不同對(duì)象,則每個(gè)線程有自己的對(duì)象的鎖,線程間彼此互不干預(yù)。 調(diào)用同一個(gè)類(lèi)中的靜態(tài)同步方法的線程將彼此阻塞,它們都是鎖定在相同的Class對(duì)象上。對(duì)于同步代碼塊,要看清楚什么對(duì)象已經(jīng)用于鎖定(synchronized后面括號(hào)的內(nèi)容)。在同一個(gè)對(duì)象上進(jìn)行同步的線程將彼此阻塞,在不同對(duì)象上鎖定的線程將永遠(yuǎn)不會(huì)彼此阻塞。線程的同步與鎖線程死鎖死鎖對(duì)程序來(lái)說(shuō),是很復(fù)雜的,也很難發(fā)現(xiàn)問(wèn)題。當(dāng)兩個(gè)線程被

23、阻塞,每個(gè)線程在等待另一個(gè)線程時(shí)就發(fā)生死鎖。實(shí)際上發(fā)生死鎖的概率很小,但是,無(wú)論代碼中發(fā)生死鎖的概率有多小,一旦發(fā)生死鎖,程序就死掉。有一些設(shè)計(jì)方法能幫助避免死鎖,包括始終按照預(yù)定義的順序獲取鎖這一策略等。線程的同步與鎖演示示例:線程死鎖線程同步小結(jié) 線程同步的目的是為了保護(hù)多個(gè)線程反問(wèn)一個(gè)資源時(shí)對(duì)資源的破壞。線程同步方法是通過(guò)鎖來(lái)實(shí)現(xiàn),每個(gè)對(duì)象都有且僅有一個(gè)鎖,這個(gè)鎖與一個(gè)特定的對(duì)象關(guān)聯(lián),線程一旦獲取了對(duì)象鎖,其他訪問(wèn)該對(duì)象的線程就無(wú)法再訪問(wèn)該對(duì)象的其他同步方法。對(duì)于靜態(tài)同步方法,鎖是針對(duì)這個(gè)類(lèi)的,鎖對(duì)象是該類(lèi)的Class對(duì)象。靜態(tài)和非靜態(tài)方法的鎖互不干預(yù)。一個(gè)線程獲得鎖,當(dāng)在一個(gè)同步方法中

24、訪問(wèn)另外對(duì)象上的同步方法時(shí),會(huì)獲取這兩個(gè)對(duì)象鎖。對(duì)于同步,要時(shí)刻清醒在哪個(gè)對(duì)象上同步,這是關(guān)鍵。線程的同步與鎖接上:編寫(xiě)線程安全的類(lèi),需要時(shí)刻注意對(duì)多個(gè)線程競(jìng)爭(zhēng)訪問(wèn)資源的邏輯和安全做出正確的判斷,對(duì)“原子”操作做出分析,并保證原子操作期間別的線程無(wú)法訪問(wèn)競(jìng)爭(zhēng)資源。當(dāng)多個(gè)線程等待一個(gè)對(duì)象鎖時(shí),沒(méi)有獲取到鎖的線程將發(fā)生阻塞。死鎖是線程間相互等待鎖鎖造成的,在實(shí)際中發(fā)生的概率非常的小,但是,一旦程序發(fā)生死鎖,程序?qū)⑺赖?。線程的同步與鎖線程交互線程交互知識(shí)涉及到j(luò)ava.lang.Object的類(lèi)的三個(gè)方法:void wait() 導(dǎo)致當(dāng)前的線程等待,直到其他線程調(diào)用此對(duì)象的 notify() 方法或 notifyAll() 方法。void notify() 喚醒在此對(duì)象監(jiān)視器上等待的單個(gè)線程。 void notifyAll() 喚醒在此對(duì)象監(jiān)視器上等待的所有線程。線程的交互 例子:當(dāng)在b對(duì)象上調(diào)用wait()

溫馨提示

  • 1. 本站所有資源如無(wú)特殊說(shuō)明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請(qǐng)下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請(qǐng)聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶(hù)所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁(yè)內(nèi)容里面會(huì)有圖紙預(yù)覽,若沒(méi)有圖紙預(yù)覽就沒(méi)有圖紙。
  • 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
  • 5. 人人文庫(kù)網(wǎng)僅提供信息存儲(chǔ)空間,僅對(duì)用戶(hù)上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對(duì)用戶(hù)上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對(duì)任何下載內(nèi)容負(fù)責(zé)。
  • 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請(qǐng)與我們聯(lián)系,我們立即糾正。
  • 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時(shí)也不承擔(dān)用戶(hù)因使用這些下載資源對(duì)自己和他人造成任何形式的傷害或損失。

評(píng)論

0/150

提交評(píng)論