最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

Java多線程編程中易混淆的3個(gè)關(guān)鍵字總結(jié)

 更新時(shí)間:2015年03月23日 09:22:18   投稿:junjie  
這篇文章主要介紹了Java多線程編程中易混淆的3個(gè)關(guān)鍵字總結(jié),本文總結(jié)了、volatile、ThreadLocal、synchronized等3個(gè)關(guān)鍵字,對(duì)這幾個(gè)容易混淆概念的關(guān)鍵字分別做了講解,需要的朋友可以參考下

概述

最近在看《ThinKing In Java》,看到多線程章節(jié)時(shí)覺(jué)得有一些概念比較容易混淆有必要總結(jié)一下,雖然都不是新的東西,不過(guò)還是蠻重要,很基本的,在開(kāi)發(fā)或閱讀源碼中經(jīng)常會(huì)遇到,在這里就簡(jiǎn)單的做個(gè)總結(jié)。

1.volatile

volatile主要是用來(lái)在多線程中同步變量。
在一般情況下,為了提升性能,每個(gè)線程在運(yùn)行時(shí)都會(huì)將主內(nèi)存中的變量保存一份在自己的內(nèi)存中作為變量副本,但是這樣就很容易出現(xiàn)多個(gè)線程中保存的副本變量不一致,或與主內(nèi)存的中的變量值不一致的情況。
而當(dāng)一個(gè)變量被volatile修飾后,該變量就不能被緩存到線程的內(nèi)存中,它會(huì)告訴編譯器不要進(jìn)行任何移出讀取和寫(xiě)入操作的優(yōu)化,換句話說(shuō)就是不允許有不同于“主”內(nèi)存區(qū)域的變量拷貝,所以當(dāng)該變量有變化時(shí),所有調(diào)用該變量的線程都會(huì)獲得相同的值,這就確保了該變量在應(yīng)用中的可視性(當(dāng)一個(gè)任務(wù)做出了修改在應(yīng)用中必須是可視的),同時(shí)性能也相應(yīng)的降低了(還是比synchronized高)。
但需要注意volatile只能確保操作的是同一塊內(nèi)存,并不能保證操作的原子性。所以volatile一般用于聲明簡(jiǎn)單類型變量,使得這些變量具有原子性,即一些簡(jiǎn)單的賦值與返回操作將被確保不中斷。但是當(dāng)該變量的值由自身的上一個(gè)決定時(shí),volatile的作用就將失效,這是由volatile關(guān)鍵字的性質(zhì)所決定的。
所以在volatile時(shí)一定要謹(jǐn)慎,千萬(wàn)不要以為用volatile修飾后該變量的所有操作都是原子操作,不再需要synchronized關(guān)鍵字了。

2.ThreadLocal

首先ThreadLocal和本地線程沒(méi)有一毛錢(qián)關(guān)系,更不是一個(gè)特殊的Thread,它只是一個(gè)線程的局部變量(其實(shí)就是一個(gè)Map),ThreadLocal會(huì)為每個(gè)使用該變量的線程提供獨(dú)立的變量副本,所以每一個(gè)線程都可以獨(dú)立地改變自己的副本,而不會(huì)影響其它線程所對(duì)應(yīng)的副本。這樣做其實(shí)就是以空間換時(shí)間的方式(與synchronized相反),以耗費(fèi)內(nèi)存為代價(jià),單大大減少了線程同步(如synchronized)所帶來(lái)性能消耗以及減少了線程并發(fā)控制的復(fù)雜度。
個(gè)人覺(jué)得比較典型的例子就是在Android關(guān)于Looper的源碼中對(duì)ThreadLocal的使用,同時(shí)也包含了ThreadLocal的基本用法,具體代碼如下:

public class Looper { 
private static final String TAG = "Looper";

// sThreadLocal.get() will return null unless you've called prepare(). 
private static final ThreadLocal sThreadLocal = new ThreadLocal(); 

...... 

private static Looper mMainLooper = null; 

...... 

public static final void prepare() { 
  if (sThreadLocal.get() != null) { 
    throw new RuntimeException("Only one Looper may be created per thread"); 
  } 
  sThreadLocal.set(new Looper()); 
} 

...... 

public static final void prepareMainLooper() { 
  prepare(); 
  setMainLooper(myLooper()); 

  ...... 

} 

private synchronized static void setMainLooper(Looper looper) { 
  mMainLooper = looper; 
} 
public synchronized static final Looper getMainLooper() { 
  return mMainLooper; 
} 

...... 

public static final Looper myLooper() { 
  return (Looper)sThreadLocal.get(); 
} 

...... 

} 


但需要注意的是,雖然ThreadLocal和Synchonized都用于解決多線程并發(fā)訪問(wèn),ThreadLocal與synchronized還是有本質(zhì)的區(qū)別。synchronized是利用鎖的機(jī)制,使變量或代碼塊在某一時(shí)該只能被一個(gè)線程訪問(wèn)。而ThreadLocal為每一個(gè)線程都提供了變量的副本,使得每個(gè)線程在某一時(shí)間訪問(wèn)到的并不是同一個(gè)對(duì)象,這樣就隔離了多個(gè)線程對(duì)數(shù)據(jù)的數(shù)據(jù)共享。而Synchronized卻正好相反,它用于在多個(gè)線程間通信時(shí)能夠獲得數(shù)據(jù)共享。即Synchronized用于線程間的數(shù)據(jù)共享,而ThreadLocal則用于線程間的數(shù)據(jù)隔離。所以ThreadLocal并不能代替synchronized,Synchronized的功能范圍更廣(同步機(jī)制)。

3.synchronized

synchronized關(guān)鍵字是Java利用鎖的機(jī)制自動(dòng)實(shí)現(xiàn)的,一般有同步方法和同步代碼塊兩種使用方式。Java中所有的對(duì)象都自動(dòng)含有單一的鎖(也稱為監(jiān)視器),當(dāng)在對(duì)象上調(diào)用其任意的synchronized方法時(shí),此對(duì)象被加鎖(一個(gè)任務(wù)可以多次獲得對(duì)象的鎖,計(jì)數(shù)會(huì)遞增),同時(shí)在線程從該方法返回之前,該對(duì)象內(nèi)其他所有要調(diào)用類中被標(biāo)記為synchronized的方法的線程都會(huì)被阻塞。當(dāng)然針對(duì)每個(gè)類也有一個(gè)鎖(作為類的Class對(duì)象的一部分),所以你懂的^.^。
最后需要注意的是synchronized是同步機(jī)制中最安全的一種方式,其他的任何方式都是有風(fēng)險(xiǎn)的,當(dāng)然付出的代價(jià)也是最大的。

相關(guān)文章

  • Java解釋器的運(yùn)行過(guò)程介紹

    Java解釋器的運(yùn)行過(guò)程介紹

    今天小編就為大家分享一篇關(guān)于Java解釋器的運(yùn)行過(guò)程介紹,小編覺(jué)得內(nèi)容挺不錯(cuò)的,現(xiàn)在分享給大家,具有很好的參考價(jià)值,需要的朋友一起跟隨小編來(lái)看看吧
    2019-04-04
  • 解決springboot bean中大寫(xiě)的字段返回變成小寫(xiě)的問(wèn)題

    解決springboot bean中大寫(xiě)的字段返回變成小寫(xiě)的問(wèn)題

    這篇文章主要介紹了解決springboot bean中大寫(xiě)的字段返回變成小寫(xiě)的問(wèn)題,具有很好的參考價(jià)值希望對(duì)大家有所幫助。一起跟隨小編過(guò)來(lái)看看吧
    2021-01-01
  • MyBatis通過(guò)BATCH批量提交的方法

    MyBatis通過(guò)BATCH批量提交的方法

    今天小編就為大家分享一篇關(guān)于MyBatis通過(guò)BATCH批量提交的方法,小編覺(jué)得內(nèi)容挺不錯(cuò)的,現(xiàn)在分享給大家,具有很好的參考價(jià)值,需要的朋友一起跟隨小編來(lái)看看吧
    2018-12-12
  • Java中g(shù)etSuperclass()方法的使用與原理解讀

    Java中g(shù)etSuperclass()方法的使用與原理解讀

    文章介紹了Java中的getSuperclass()方法,該方法用于獲取一個(gè)類的直接父類,通過(guò)理解其使用方式、工作原理以及實(shí)際應(yīng)用場(chǎng)景,可以更好地利用反射機(jī)制處理類的繼承關(guān)系,實(shí)現(xiàn)動(dòng)態(tài)類型檢查、類加載以及序列化等功能
    2025-01-01
  • SpringBoot使用Spark過(guò)程詳解

    SpringBoot使用Spark過(guò)程詳解

    這篇文章主要介紹SpringBoot使用Spark的方法的相關(guān)知識(shí),小編通過(guò)實(shí)際案例向大家展示操作過(guò)程,操作方法簡(jiǎn)單快捷,實(shí)用性強(qiáng),希望能幫助大家解決問(wèn)題
    2023-02-02
  • java使用定時(shí)器實(shí)現(xiàn)監(jiān)聽(tīng)數(shù)據(jù)變化

    java使用定時(shí)器實(shí)現(xiàn)監(jiān)聽(tīng)數(shù)據(jù)變化

    這篇文章主要為大家詳細(xì)介紹了Java如何使用定時(shí)器監(jiān)聽(tīng)數(shù)據(jù)變化,當(dāng)滿足某個(gè)條件時(shí)(例如沒(méi)有數(shù)據(jù)更新)自動(dòng)執(zhí)行某項(xiàng)任務(wù),有興趣的可以了解下
    2023-11-11
  • Java橋梁設(shè)計(jì)模式優(yōu)雅地將抽象與實(shí)現(xiàn)分離

    Java橋梁設(shè)計(jì)模式優(yōu)雅地將抽象與實(shí)現(xiàn)分離

    Java橋接設(shè)計(jì)模式通過(guò)將抽象和實(shí)現(xiàn)分離,使得它們可以獨(dú)立地變化,從而實(shí)現(xiàn)更靈活的代碼結(jié)構(gòu)。它是一種優(yōu)雅的設(shè)計(jì)模式,適用于需要處理多個(gè)變化因素的復(fù)雜應(yīng)用程序
    2023-04-04
  • 解決Java處理HTTP請(qǐng)求超時(shí)的問(wèn)題

    解決Java處理HTTP請(qǐng)求超時(shí)的問(wèn)題

    這篇文章主要介紹了解決Java處理HTTP請(qǐng)求超時(shí)的問(wèn)題,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過(guò)來(lái)看看吧
    2021-03-03
  • Java 進(jìn)行時(shí)間處理的步驟

    Java 進(jìn)行時(shí)間處理的步驟

    時(shí)間處理是常見(jiàn)的需求,本文將講述Java語(yǔ)言如何進(jìn)行時(shí)間處理,感興趣的朋友可以了解下
    2021-05-05
  • 通過(guò)FeignClient如何獲取文件流steam?is?close問(wèn)題

    通過(guò)FeignClient如何獲取文件流steam?is?close問(wèn)題

    這篇文章主要介紹了通過(guò)FeignClient如何獲取文件流steam?is?close問(wèn)題,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2022-06-06

最新評(píng)論

博客| 北流市| 历史| 社旗县| 偃师市| 安阳市| 苗栗县| 黄冈市| 辉南县| 孟州市| 长治县| 金门县| 固原市| 西充县| 仙居县| 若尔盖县| 武安市| 垣曲县| 关岭| 绥德县| 奎屯市| 临湘市| 信丰县| 稷山县| 道孚县| 嘉祥县| 饶阳县| 西畴县| 武胜县| 屯留县| 蓬莱市| 长寿区| 灵寿县| 靖安县| 漳浦县| 东乡族自治县| 襄垣县| 徐州市| 玉门市| 乐山市| 卓资县|