我想到調用realloc太多次不會那麼聰明。
你是怎麼想出來的?因爲唯一真正知道的方法是衡量表現。
根據用戶如何閱讀數據,您的策略可能需要不同。如果您使用的是getchar()
,則每次讀取字符時,您可能不希望使用realloc()
將緩衝區大小增加一個字符。但是,即使在這種情況下,好的realloc()
的效率也會比您想象的低得多。我認爲,glibc實際給你的最小塊大小爲malloc()
,這是16字節。因此,從0到16個字符並重新分配每次不涉及任何複製。類似地,對於較大的重新分配,可能不需要分配新塊,可以使現有塊更大。不要忘記,即使速度最慢,realloc()
也會比人們輸入的速度快。
大多數人不會選擇這種策略。可以輸入什麼類型的內容,因此人們輸入非常快的參數不一定有效。通常,您會介紹容量的概念。您分配具有一定容量的緩衝區,當它滿了時,通過添加一定大小的新區塊來增加容量(使用realloc()
)。初始大小和重新分配大小可以通過各種方式進行調整。如果您正在閱讀用戶輸入內容,則可能需要較小的值,例如256字節,如果您正在從磁盤或整個網絡讀取文件,則可能需要更大的值,例如4Kb或更大。
增量大小甚至不需要保持不變,您可以選擇將每個所需重新分配的大小加倍。這是一些編程庫使用的策略。例如,哈希表的Java實現使用它我相信,所以可能做一個數組的可可實現。
事先不可能知道在任何特定情況下最好的策略是什麼。我會選擇一些感覺不錯的東西,然後,如果應用程序有性能問題,我會做測試來調整它。您的代碼不一定是最快的,但速度不夠快。
但是我絕對不會做的一件事是覆蓋家庭滾動內存算法覆蓋內置分配器的頂部。如果你發現自己保留了一個你沒有使用的塊列表,而不是釋放它們,那麼你做錯了。這是OpenSSL陷入困境的原因。
是的,這被稱爲內存池,通常這是一個好主意。 – arrowd
可以說,將緩衝區大小增加一倍,而不是增加一定數量會更好。 – silel
你在優化,速度或內存使用?如果你預先分配100MB的數據,你幾乎不需要調用'realloc'。可能是最快的。 –