2009-05-27 71 views
0

我寫了一個小型的內部C#程序,它在各種文件格式之間批量轉換,主要依賴於其他API。目前,UI生成一個BackgroundWorker(不是線程)來處理轉換,然後用作爲工作者完成作業時清空的請求填充隊列。隊列對象本身非常小(3個字符串,告訴工作人員該做什麼),並且對程序的內存佔用量沒有太大貢獻。我的內存管理非常嚴格(完成後丟棄圖像,並在某些時候手動進行垃圾收集)。但是,程序一次只能使用大約100 MB的內存,並且佔用了大約50%的內存總CPU時間。這似乎是如果我天真地執行線程,它會很快用完系統內存(除非CLR做了某種我不知道的魔法)。防止多線程應用程序內存不足

是否有一種簡單/有效的方法來產生線程來防止除了捕獲OutOfMemory異常並回滾已死的線程(似乎效率很低,但沒有辦法在不使用大量內存的情況下保留狀態)之外,系統還會耗盡內存。

+2

我們在說多少個話題?你提到UI和一名工作人員......但這不應該是一個大問題;你是否會產生很多線程? – 2009-05-27 20:30:42

回答

2

如果您使用ThreadPool.QueueUserWorkItem產生轉換,您將自動獲得正在運行的線程數的限制。 ThreadPool在內部進行管理,並在池線程可用時立即處理排隊調用。

0

對隊列大小設置限制,並使發送者等待已滿。但是,您必須憑經驗找到正確的隊列大小限制。

0

內存不足異常可能會非常棘手,可能由內存碎片引起,而不是實際內存不足。因此,他們可能很難追查。

來自Sweeden的微軟產品支持Tess(http://blogs.msdn.com/tess/)已經獲得了很多關於追蹤內存的帖子,內存將幫助這個過程。

您的應用程序的良好形象也可以幫助。 JetBrains和AQTime一樣都很好。

0

使用100MB內存對於圖像處理應用程序並不是很多。

另外,在.net中,當你得到一個OutOfMemory異常時,整個過程就會消失,你無法從中恢復。

如果你需要更多的內存(或者更準確的說,更多的地址空間),那麼當你使用它或者切換到64位時,系統可以給你任意頁面內存。

您可以限制隊列大小以確保唯一的「重」內存用戶是工作者線程,可以有多個工作線程,這會增加內存使用量,但也會更快地清空隊列,只記得在像這樣的CPU密集型操作中具有比CPU核更多的線程是低效的。

你說的是「天真實現的線程」,多線程充滿了陷阱 - 一個天真的實現將效率低下,充滿了錯誤。