Dot-Net

Dispose 方法的執行緒安全?

  • February 17, 2011

MSDN 很好地記錄了 BCL 類型的實例成員的執行緒安全性,但我從未真正看到指示如何呼叫類型Dispose方法的資訊。IDisposable

方法 a)是否Dispose保證對所有類都是執行緒安全的,b) 從不保證是執行緒安全的,c) 是否保證對某些類是執行緒安全的(如果是這樣,具體記錄在哪裡)?

最後,如果Dispose保證方法是執行緒安全的,那是否意味著我必須在使用一次性資源的類中的每個實例方法周圍加鎖?

旁白:我知道類型的終結器應該是執行緒安全的,因為垃圾收集在 .NET 中的工作方式(非常積極),並且它們可能會呼叫該Dispose方法。但是,讓我們把這個問題放在一邊。

執行緒安全和 Dispose 的問題有些棘手。由於在許多情況下,一旦任何其他執行緒開始處置對象,任何執行緒唯一可以合法地對對像做的事情就是嘗試處置它自己,乍一看,確保執行緒安全所需的唯一事情就是在 ‘disposed’ 標誌上使用 Interlocked.Exchange 以確保一個執行緒的 Dispose 嘗試發生,而另一個執行緒被靜默忽略。事實上,這是一個很好的起點,我認為它應該是標準 Dispose 模式的一部分(CompareExchange 應該在密封的基類包裝方法中完成,以避免每個派生類都需要使用自己的私有處置標誌)。不幸的是,如果考慮 Dispose 的實際作用,事情就會復雜得多。

Dispose 的真正目的不是對正在處理的對像做某事,而是清理該對象持有引用的其他實體。這些實體可能是被管理的對象、系統對象,或者完全是其他東西;它們甚至可能與正在處理的對像不在同一台電腦上。為了使 Dispose 成為執行緒安全的,那些其他實體將允許 Dispose 在其他執行緒可能正在使用它們做其他事情的同時清理它們。一些對象可以處理這種用法;其他人不能。

一個特別令人煩惱的例子:對像被允許有帶有非執行緒安全的 RemoveHandler 方法的事件。因此,任何清理事件處理程序的 Dispose 方法都只能從與創建訂閱的執行緒相同的執行緒中呼叫。

引用自:https://stackoverflow.com/questions/5024883