2011-10-06 42 views
1

我有一個函數需要一個字符串數組(緩衝區)並需要增加它的大小。 因此,我調用realloc的分配字符串數組的最快方法

temp = (char**) realloc (buffer, newSize * (sizeof(char*))); 
if (temp == NULL) 
    return false; 
else 
    buffer = temp; 

因此到目前爲止,一切都很好。現在對於每個新的單元格,我都必須調用正確大小的malloc。注意newSize總是偶數,並且奇數字符串的長度與偶數字符串的長度不同。

for (i = oldSize; i < newSize; i++){ 
    support = (char*) malloc (LENGTH1 * sizeof(char)); 
    if (support == NULL){ 
     marker = i; 
     failedMalloc = true; 
     break; 
    } 
    else 
     buffer[i] = support; 

    i++; 

    support = (char*) malloc (LENGTH2 * sizeof(char)); 
    if (support == NULL){ 
     marker = i; 
     failedMalloc = true; 
     break; 
    } 
    else 
     buffer[i] = support; 

} 

事實是,自從我與海量數據的工作我遲早會完成內存和realloc的或mallocs將失敗之一。問題是,如果它是malloc中的一個,那麼失敗的風險是我必須自由調用百萬來清除一些內存。這需要很長時間。有什麼辦法可以加速這個過程,甚至更好地避免它?

if (failedMalloc){ 
    for (i = oldRows; i < marker; i++) 
     free(buffer[i]); 
    temp = (char**) realloc (buffer, oldRows * (sizeof(char*))); 
} 

PS:是的我知道指針算術比數組索引更快。當我找到解決這個問題的方法時,我會實現它,因爲我更喜歡使用數組索引,因爲我覺得它不太容易出錯。但最終版本將使用指針算術

+0

指針的運算速度不及數組索引 – sth

+0

@sth,我在基準測試中發現了同樣的情況 - x86架構在指令級別內置了索引,所以如果您正在循環索引你可以免費得到它。 –

+0

@sth:什麼架構? –

回答

4

而不是分別分配每個字符串,分塊分配它們。你可以例如malloc 128 *(LENGTH1 + LENGTH2),並有256個連續字符串的空間。無論何時你的索引越過一個塊邊界,malloc是另一個大塊,並使用模算術來得到一個字符串開始的偏移量。

P.S. sizeof(char)保證是1.

+0

該概念上的變體:malloc((newSize/2)*(LENGTH1 + LENGTH2)+(newSize&1?LENGTH1:0)); – mjfgates

+0

只需要記住不要在這種情況下單獨釋放每個字符串......只需要每個字符串塊,而不再需要塊中的任何字符串。另外,如果他在這樣的循環中填入單個字符串的地址,他可以輕鬆地使用指針算術而不是模算術來獲得他們的地址,如果他喜歡的話。 – Dmitri

+0

你能給我一個小樣本源代碼嗎?我不確定我是否理解你的建議。特別是我不明白如何訪問這些字符串,因爲我試過的東西崩潰了。此外,我不知道它是否重要,但我不能使用malloc(),我必須重新分配(),因爲我正在增加一個已經存在的數組。 – Alex

0

你可以編寫你自己的分配和釋放例程,並使用它們而不是malloc/free作爲字符串。如果你的例程是一個或多個大緩衝區,並將其中的一小部分緩衝區分出來,那麼只需在每個大緩衝區上調用free即可釋放整個區塊。

在所有分配的大小相同的情況下,這種總體思路特別適用,在這種情況下,它被稱爲「池分配器」。在這種情況下,對於每個陣列或字符串,您可以爲LENGTH1分配擁有一個關聯池,另一個用於LENGTH2

我說「寫你自己的」,但毫無疑問,在那裏有簡單的開源池分配器。避免浪費存儲器

0

的一種方式是每次MALLOC更大的存儲器,當需要對malloc,

malloc的固定大小(對準2^N),例如

int m_size = 1; 

// when need malloc 
while (m_size < require_size) m_size * 2; 
malloc(m_size); 
1

分配更大的內存塊。越少的malloc呼叫越好。最快的將是預先計算所需的大小並只分配一次。

此外,使用指針算術在這裏不會產生任何可見的差異。

相關問題