国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 學(xué)院 > 開發(fā)設(shè)計(jì) > 正文

.NET多線程編程(3):線程同步

2019-11-17 04:06:37
字體:
供稿:網(wǎng)友
隨著對多線程學(xué)習(xí)的深入,你可能覺得需要了解一些有關(guān)線程共享資源的問題. .NET framework提供了很多的類和數(shù)據(jù)類型來控制對共享資源的訪問。

考慮一種我們經(jīng)常遇到的情況:有一些全局變量和共享的類變量,我們需要從不同的線程來更新它們,可以通過使用System.Threading.Interlocked類完成這樣的任務(wù),它提供了原子的,非模塊化的整數(shù)更新操作。

還有你可以使用System.Threading.Monitor類鎖定對象的方法的一段代碼,使其暫時(shí)不能被別的線程訪問。

System.Threading.WaitHandle類的實(shí)例可以用來封裝等待對共享資源的獨(dú)占訪問權(quán)的操作系統(tǒng)特定的對象。尤其對于非受管代碼的互操作問題。

System.Threading.Mutex用于對多個(gè)復(fù)雜的線程同步的問題,它也允許單線程的訪問。

像ManualResetEvent和AutoResetEvent這樣的同步事件類支持一個(gè)類通知其他事件的線程。

不討論線程的同步問題,等于對多線程編程知之甚少,但是我們要十分謹(jǐn)慎的使用多線程的同步。在使用線程同步時(shí),我們事先就要要能夠正確的確定是那個(gè)對象和方法有可能造成死鎖(死鎖就是所有的線程都停止了相應(yīng),都在等者對方釋放資源)。還有贓數(shù)據(jù)的問題(指的是同一時(shí)間多個(gè)線程對數(shù)據(jù)作了操作而造成的不一致),這個(gè)不容易理解,這么說吧,有X和Y兩個(gè)線程,線程X從文件讀取數(shù)據(jù)并且寫數(shù)據(jù)到數(shù)據(jù)結(jié)構(gòu),線程Y從這個(gè)數(shù)據(jù)結(jié)構(gòu)讀數(shù)據(jù)并將數(shù)據(jù)送到其他的計(jì)算機(jī)。假設(shè)在Y讀數(shù)據(jù)的同時(shí),X寫入數(shù)據(jù),那么顯然Y讀取的數(shù)據(jù)與實(shí)際存儲的數(shù)據(jù)是不一致的。這種情況顯然是我們應(yīng)該避免發(fā)生的。少量的線程將使得剛才的問題發(fā)生的幾率要少的多,對共享資源的訪問也更好的同步。

.NET Framework的CLR提供了三種方法來完成對共享資源 ,諸如全局變量域,特定的代碼段,靜態(tài)的和實(shí)例化的方法和域。

(1)       代碼域同步:使用Monitor類可以同步靜態(tài)/實(shí)例化的方法的全部代碼或者部分代碼段。不支持靜態(tài)域的同步。在實(shí)例化的方法中,this指針用于同步;而在靜態(tài)的方法中,類用于同步,這在后面會講到。

(2)       手工同步:使用不同的同步類(諸如WaitHandle, Mutex, ReaderWriterLock, ManualResetEvent, AutoResetEvent 和Interlocked等)創(chuàng)建自己的同步機(jī)制。這種同步方式要求你自己手動(dòng)的為不同的域和方法同步,這種同步方式也可以用于進(jìn)程間的同步和對共享資源的等待而造成的死鎖解除。

(3)       上下文同步:使用SynchronizationAttribute為ContextBoundObject對象創(chuàng)建簡單的,自動(dòng)的同步。這種同步方式僅用于實(shí)例化的方法和域的同步。所有在同一個(gè)上下文域的對象共享同一個(gè)鎖。



Monitor Class



在給定的時(shí)間和指定的代碼段只能被一個(gè)線程訪問,Monitor 類非常適合于這種情況的線程同步。這個(gè)類中的方法都是靜態(tài)的,所以不需要實(shí)例化這個(gè)類。下面一些靜態(tài)的方法提供了一種機(jī)制用來同步對象的訪問從而避免死鎖和維護(hù)數(shù)據(jù)的一致性。

Monitor.Enter 方法:在指定對象上獲取排他鎖。

Monitor.TryEnter 方法:試圖獲取指定對象的排他鎖。

Monitor.Exit 方法:釋放指定對象上的排他鎖。

Monitor.Wait 方法:釋放對象上的鎖并阻塞當(dāng)前線程,直到它重新獲取該鎖。

Monitor.Pulse 方法:通知等待隊(duì)列中的線程鎖定對象狀態(tài)的更改。

Monitor.PulseAll 方法:通知所有的等待線程對象狀態(tài)的更改。

通過對指定對象的加鎖和解鎖可以同步代碼段的訪問。Monitor.Enter, Monitor.TryEnter 和 Monitor.Exit用來對指定對象的加鎖和解鎖。一旦獲取(調(diào)用了Monitor.Enter)指定對象(代碼段)的鎖,其他的線程都不能獲取該鎖。舉個(gè)例子來說吧,線程X獲得了一個(gè)對象鎖,這個(gè)對象鎖可以釋放的(調(diào)用Monitor.Exit(object) or Monitor.Wait)。當(dāng)這個(gè)對象鎖被釋放后,Monitor.Pulse方法和 Monitor.PulseAll方法通知就緒隊(duì)列的下一個(gè)線程進(jìn)行和其他所有就緒隊(duì)列的線程將有機(jī)會獲取排他鎖。線程X釋放了鎖而線程Y獲得了鎖,同時(shí)調(diào)用Monitor.Wait的線程X進(jìn)入等待隊(duì)列。當(dāng)從當(dāng)前鎖定對象的線程(線程Y)受到了Pulse或PulseAll,等待隊(duì)列的線程就進(jìn)入就緒隊(duì)列。
發(fā)表評論 共有條評論
用戶名: 密碼:
驗(yàn)證碼: 匿名發(fā)表
主站蜘蛛池模板: 平阳县| 临泉县| 临西县| 九江县| 黑山县| 宁城县| 乐都县| 九龙县| 精河县| 乃东县| 沙坪坝区| 瑞丽市| 九江县| 千阳县| 博罗县| 子洲县| 五常市| 石柱| 巴南区| 定远县| 龙门县| 资阳市| 小金县| 萨迦县| 绍兴县| 四会市| 台前县| 保定市| 琼结县| 瑞安市| 道真| 浦县| 巴青县| 华坪县| 师宗县| 精河县| 鄂托克前旗| 会昌县| 太谷县| 新兴县| 京山县|