2011-02-13 14 views
0

在問這個問題之前,我嘗試瞭解(在SOF和其他某些網站上)的故障安全功能。我瞭解Java Collection迭代器是快速失敗的,這意味着只要底層集合正在進行結構修改(即使是相同的線程),它們也會優雅地失敗。我的問題是fail-safe屬性和Iterators的remove()或add()特性有什麼關係?在我的理解中,因爲通過迭代器,您可以在迭代集合的同時添加或刪除(安全地),並且不會得到併發異常(您不需要使用它們的刪除和添加功能),以便使得迭代器可以進行故障保護。或者我完全錯了?FailSafe功能

謝謝!

+0

請參閱我的更新。 – 2011-02-14 03:03:03

回答

2

不完全。在我的理解中,故障安全迭代器在數據快照上工作,並確保在創建迭代器時統一表示集合的視圖。 (請參閱this blog post瞭解更詳細的處理方法)。這個屬性是保證f.i.通過迭代器的CopyOnWriteArrayList。它的迭代器不支持收集修改操作和javadoc中進一步明確自己的行爲:

這個數組的 壽命迭代的過程中不會改變,所以 干擾是不可能的, 迭代器保證不會拋出 ConcurrentModificationException的。 迭代器將不會反映添加, 刪除或自從創建迭代器的 以來對列表的更改。 不支持 迭代器本身(刪除,設置和 添加)的元素更改操作。這些方法 拋出UnsupportedOperationException。

UPDATE:

當談論故障safeness和故障牢度它單獨的「失敗」是很重要的。迭代器有不同的情況和危害。至於鏈接的文章,我會說那裏的作者通過實現迭代器首先實現了故障安全和快速失敗的迭代迭代

在這種情況下的失敗可以定義爲迭代集合的併發修改。當收集被修改時,快速失敗的方法是停止迭代並使呼叫者知道改變的條件(通過CME或通過其他方式)。

當處理相同的用例和危險時,我們可以前進並思考故障安全迭代。故障安全屬性意味着只要可能(並且通過複製基礎數據成功執行該操作)迭代應該符合其合同。

+0

謝謝亞歷克斯,我想我以前讀過這個博客,我無法得到我的問題的答案,他創建了兩個迭代器,一個沒有副本,另一個沒有副本,然後說沒有副本的一個會在修改時拋出異常。我認爲即使沒有複製,你也可以進行失效保護,你只需要繼續檢查是否有任何修改。 – Abidi 2011-02-13 19:24:50

+1

故障安全只是一個屬性,他的實現通過提供副本來保證它。如果你能保證其他方面的失敗安全,那就意味着它取決於你。當您檢查修改並發現集合已被修改時,您將如何保證此屬性?順便說一句,你有沒有閱讀該博客文章中提到的維基百科的參考? – 2011-02-13 19:27:04

0

IteratorListIterator工作在底層集合是一種不會使Iterator無效的方式。通過任何其他迭代器或集合本身進行的任何修改都會使迭代器對某些集合失效。有些集合是爲併發訪問而設計的,並沒有這個限制。