2011-09-14 81 views
3

是否有更好的方式根據條件從哈希表中移除多個項目,而不是先將項目保存在列表中,然後迭代並逐個刪除每個項目?通用列表提供了一個「RemoveAll」方法,我可以傳遞一個匿名函數,但似乎並沒有對HashTable的等效方法。注意:我正在使用.NET框架2.0從循環中移除哈希表中的項目

+0

你有沒有嘗試過hashtable.Remove方法 – 62071072SP

+0

它是多線程應用程序嗎? –

+0

它不是多線程的,並且可以使用hashtable.remove方法,但是我需要循環兩次,一次找到要刪除的鍵,然後再次循環通過鍵集合以分別刪除每個鍵(沒有任何東西removeRange方法,我可以傳遞一組鍵) – RKP

回答

0

這真的取決於您的應用程序。如果您的應用程序是多線程的,並且使用.NET 4.0,通常最好使用ReaderWriterLock/ReaderWriterLockSlim並獲取讀卡器鎖定,構建要刪除的密鑰列表,然後升級到寫入鎖定並執行循環在列表中刪除密鑰。這樣,當您通過Hashtable來反覆刪除鍵時,其他讀者可以在不被鎖定的情況下訪問它。

現在,如果你可以使用.NET 4.0,那麼ConcurrentDictionary就很棒了,而且競爭也更少!如果你停留在.NET 2.0中,我推薦Dictionary,儘管它本身不是你問題的一部分。

UPDATE如果您的申請不多線程,無需鎖定,但你仍然需要建立密鑰列表中,因爲調用remove(),而迭代無效枚舉。所以基本上,你考慮到你對問題的評論是正確的。

+0

謝謝,我正在處理遺留代碼。你的意思是我必須把散列表轉換成字典嗎?即使那麼它將如何解決這個問題呢?它有更好的API來操縱集合嗎? – RKP

+0

@RKP:不,只是微軟的建議,總是喜歡通用集合的原始集合。更高性能,非裝箱等等。但是,如果它是傳統代碼,那麼你只需要使用你所處理的內容:-) –

0

據我所知。只是迭代你的列表並按照這種方式刪除密鑰有什麼問題?如果你經常這樣做,只需將它變成一個函數...

如果你使用.NET framework 3.5或更高版本,LINQ可能會讓你的目標更容易完成。

+1

不幸的是,LINQ並沒有對序列提供變異操作(即不添加,刪除等)。 –

+0

沒錯,但是你可以創建一個元素只匹配(a)條件的序列的副本。 –

+0

沒錯,儘管實質上你仍然在製作一系列的結果來刪除。簡化查詢過程,但1)make列表2)從列表中逐個刪除所有密鑰 - 仍然是相同的算法。這是主要的觀點。我同意LINQ查詢更容易做出列表。 –