摘要:并發(fā)數(shù)據(jù)結(jié)構(gòu)存在的理由串行數(shù)據(jù)結(jié)構(gòu)在并發(fā)環(huán)境下是不安全的,而直接使用鎖又會(huì)帶來性能的影響,所以專門設(shè)計(jì)了針對(duì)并發(fā)環(huán)境下的數(shù)據(jù)結(jié)構(gòu),其中使用了無鎖運(yùn)算來保證性能。在高并發(fā)的情況下過多的鎖操作會(huì)拖累系統(tǒng)的性能。是由數(shù)組結(jié)構(gòu)和數(shù)組結(jié)構(gòu)組成。
【并發(fā)數(shù)據(jù)結(jié)構(gòu)存在的理由
串行數(shù)據(jù)結(jié)構(gòu)在并發(fā)環(huán)境下是不安全的,而直接使用鎖又會(huì)帶來性能的影響,所以jdk專門設(shè)計(jì)了針對(duì)并發(fā)環(huán)境下的數(shù)據(jù)結(jié)構(gòu),其中使用了無鎖運(yùn)算來保證性能。
【并發(fā)List1.可以直接使用Collections.synchronizedList()將一個(gè)非線程安全的list變成支持同步的list.但是這樣做有一個(gè)問題,就是所有的操作都會(huì)被加上鎖,我們知道如果只有讀操作是不需要上鎖的。
2..CopyOnWriteArrayList:使用了無鎖計(jì)算,即當(dāng)對(duì)象進(jìn)行寫操作時(shí),復(fù)制該對(duì)象;若進(jìn)行讀,則直接返回結(jié)果,操作過程中不進(jìn)行同步。這很好的利用了對(duì)象的不變性,在沒有對(duì)對(duì)像進(jìn)行寫操作之前,由于對(duì)象未發(fā)生改變,因此不需要加鎖。而在試圖改變對(duì)象的時(shí)候,總是先獲得一個(gè)對(duì)象的副本,然后對(duì)副本進(jìn)行操作,最后將副本寫回。這種實(shí)現(xiàn)方式的核心思想時(shí)減少競(jìng)爭(zhēng),從而提高在高并發(fā)時(shí)的讀取性能。但是在一定程度上犧牲了寫的性能。
3.Vector:使用了同步關(guān)鍵字,所有的get操作都需要先獲得鎖才能進(jìn)行。在高并發(fā)的情況下過多的鎖操作會(huì)拖累系統(tǒng)的性能。
結(jié)論:在讀多寫少的環(huán)境下,使用CopyOnWriteArrayList可以提高性能,但是在寫多讀少的環(huán)境下,應(yīng)該使用vector.
【并發(fā)set與list相似,并發(fā)set也有一個(gè)CopyOnWriteArraySet,它實(shí)現(xiàn)了set接口,并且是線程安全的,它的內(nèi)部完全依賴CopyOnWriteArrayList,因此它的特征和CopyOnWriteArrayList一致,適用于讀多寫少的環(huán)境,如果是寫多讀少的環(huán)境可以使用Collections.synchronizedSet()得到一個(gè)線程安全的set。
【并發(fā)map同理獲得一個(gè)線程安全的map也可以使用Collections.synchronizedMap(),但是在高并發(fā)的環(huán)境下這個(gè)map的性能不是最佳的。Jdk專門提供了一個(gè)cocurrentHashMap來支持高并發(fā)。而cocurrentHashMap之所以如此強(qiáng)大,是因?yàn)椋?/p>
1. 其內(nèi)部實(shí)現(xiàn)了鎖分離。 2. get()操作也是無鎖的。【cocurrentHashMap:
ConcurrentHashMap是由Segment數(shù)組結(jié)構(gòu)和HashEntry數(shù)組結(jié)構(gòu)組成。Segment是一種可重入鎖ReentrantLock,在ConcurrentHashMap里扮演鎖的角色,HashEntry則用于存儲(chǔ)鍵值對(duì)數(shù)據(jù)。一個(gè)ConcurrentHashMap里包含一個(gè)Segment數(shù)組,Segment的結(jié)構(gòu)和HashMap類似,是一種數(shù)組和鏈表結(jié)構(gòu), 一個(gè)Segment里包含一個(gè)HashEntry數(shù)組,每個(gè)HashEntry是一個(gè)鏈表結(jié)構(gòu)的元素, 每個(gè)Segment守護(hù)者一個(gè)HashEntry數(shù)組里的元素,當(dāng)對(duì)HashEntry數(shù)組的數(shù)據(jù)進(jìn)行修改時(shí),必須首先獲得它對(duì)應(yīng)的Segment鎖。
而HashTable則是使用了內(nèi)部鎖,所有的操作全部都需要獲得內(nèi)部鎖才能得以執(zhí)行。
但是呢,使用所分離這樣的技術(shù)也有一個(gè)缺點(diǎn):當(dāng)需要統(tǒng)計(jì)全局變量時(shí)(比如count),我們需要獲得所有分段鎖才能夠執(zhí)行。
文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請(qǐng)注明本文地址:http://systransis.cn/yun/68087.html
摘要:我的是忙碌的一年,從年初備戰(zhàn)實(shí)習(xí)春招,年三十都在死磕源碼,三月份經(jīng)歷了阿里五次面試,四月順利收到實(shí)習(xí)。因?yàn)槲倚睦砗芮宄?,我的目?biāo)是阿里。所以在收到阿里之后的那晚,我重新規(guī)劃了接下來的學(xué)習(xí)計(jì)劃,將我的短期目標(biāo)更新成拿下阿里轉(zhuǎn)正。 我的2017是忙碌的一年,從年初備戰(zhàn)實(shí)習(xí)春招,年三十都在死磕JDK源碼,三月份經(jīng)歷了阿里五次面試,四月順利收到實(shí)習(xí)offer。然后五月懷著忐忑的心情開始了螞蟻金...
摘要:介紹中無鎖的線程安全整數(shù),一個(gè)提供原子操作的的類。在語言中,和操作并不是線程安全的,在使用的時(shí)候,不可避免的會(huì)用到關(guān)鍵字。而則通過一種線程安全的加減操作接口。就是的意思,比較并操作。有個(gè)操作數(shù),內(nèi)存值,舊的預(yù)期值,要修改的新值。 【介紹 JAVA 中無鎖的線程安全整數(shù) AtomicInteger,一個(gè)提供原子操作的Integer的類。在Java語言中,++i和i++操作并不是線程安全的...
摘要:在中一般來說通過來創(chuàng)建所需要的線程池,如高并發(fā)原理初探后端掘金閱前熱身為了更加形象的說明同步異步阻塞非阻塞,我們以小明去買奶茶為例。 AbstractQueuedSynchronizer 超詳細(xì)原理解析 - 后端 - 掘金今天我們來研究學(xué)習(xí)一下AbstractQueuedSynchronizer類的相關(guān)原理,java.util.concurrent包中很多類都依賴于這個(gè)類所提供的隊(duì)列式...
摘要:在中一般來說通過來創(chuàng)建所需要的線程池,如高并發(fā)原理初探后端掘金閱前熱身為了更加形象的說明同步異步阻塞非阻塞,我們以小明去買奶茶為例。 AbstractQueuedSynchronizer 超詳細(xì)原理解析 - 后端 - 掘金今天我們來研究學(xué)習(xí)一下AbstractQueuedSynchronizer類的相關(guān)原理,java.util.concurrent包中很多類都依賴于這個(gè)類所提供的隊(duì)列式...
閱讀 796·2021-08-23 09:46
閱讀 946·2019-08-30 15:44
閱讀 2603·2019-08-30 13:53
閱讀 3050·2019-08-29 12:48
閱讀 3872·2019-08-26 13:46
閱讀 1807·2019-08-26 13:36
閱讀 3520·2019-08-26 11:46
閱讀 1419·2019-08-26 10:48