1. 程式人生 > >以redis為例說明記憶體碎片問題

以redis為例說明記憶體碎片問題

When Redis runs, lots of different things are allocated, such as dictionaries to allow O(1) lookups, metadata for 
objects, VM metadata. All these things need to be in memory, but aren't there from the start. So, when you 
gradually add a lot of data to an empty db, these things are allocated as well. Now, when these objects are 
free'd, some other objects are not (like some dictionary stuff, etc). This causes heavy memory fragmentation. 
When the operating system hands out blocks of memory, these blocks are often 4096 bytes in size. When 
there is only 1 byte allocated by Redis on this 4k block, the OS sees this entire block as being used by Redis.

To return to your question: when there is metadata that is not free'd on FLUSHALL and it quit heavily 
fragmented, there are a lot of gaps of unused memory in the entire space occupied by Redis. When new 
objects are again allocated, these gaps are used. You will see that if you load the dataset again, you will not 
see (a large) increase in memory usage. I hope this helps in understanding these memory properties!

上面的分析使我對之前遇到的一個問題豁然開朗,當時是自己寫的一個TCP服務端程式,它不停的接收資料包並處理。但當它處於空閒狀態時,是沒有大量記憶體使用的,但是ps的
結果上看使用記憶體使用量(VIRT)往往達到百兆以上,其原因就是因為使用了STL的QUEUE來儲存收到的資料包,當所有的資料包空間被釋放後,QUEUE會進行一定的預留,進而引
起了記憶體碎片。