2011-03-04 28 views
1

我使用Shawn Chin在這裏發佈的方法生成連續的二維數組[1] [2]它工作得很好。從他的崗位連續二維數組的重新分配

簡述:

char** allocate2Dchar(int count_x, int count_y) { 
    int i; 

    # allocate space for actual data 
    char *data = malloc(sizeof(char) * count_x * count_y); 

    # create array or pointers to first elem in each 2D row 
    char **ptr_array = malloc(sizeof(char*) * count_x); 
    for (i = 0; i < count_x; i++) { 
     ptr_array[i] = data + (i*count_y); 
    } 
    return ptr_array; 
} 

與以下免費功能:

void free2Dchar(char** ptr_array) { 
    if (!ptr_array) return; 
    if (ptr_array[0]) free(ptr_array[0]); 
    free(ptr_array); 
} 

這不是明擺着要我如何創建在任何尺寸等效再分配功能,雖然我只有興趣在保持連續性的同時重新分配行數。增加列的數量將會很有趣,但可能相當困難。除了說「這很難!」之外,我還沒有發現任何關於這個問題的直接討論。[2]

當然這可以通過一個可怕的蠻力方法,將數據複製到一個新的1D數組(上面的數據)進行存儲,重新分配一維數組,然後釋放並重新生成指針(ptr_array)到用於新尺寸的行元素。但是,這對於行修改來說非常緩慢,因爲有必要將內存需求至少增加一倍以便複製數據,而這對於更改列的數量確實非常糟糕。

這是用於更改行數的一種示例(對於更改列數將無法正常工作,因爲指針的偏移對於數據而言是錯誤的)。我還沒有完全測試這一點,但你的想法...

double ** 
reallocate_double_array (double **ptr_array, int count_row_old, int count_row_new, int count_col) 
{ 
    int i; 
    int old_size = count_row_old * count_col; 
    int new_size = count_row_new * count_col; 

    double *data = malloc (old_size * sizeof (double)); 
    memcpy (&data[0], &ptr_array[0][0], old_size * sizeof (double)); 
    data = realloc (data, new_size * sizeof (double)); 

    free (ptr_array[0]); 
    free (ptr_array); 

    ptr_array = malloc (count_row_new, sizeof (double *)); 

    for (i = 0; i < count_row_new; i++) 
    ptr_array[i] = data + (i * count_col); 

    return ptr_array; 
} 

此外,這種方法需要你知道以前的大小,這是很厲害的!

任何想法非常感謝。

[1] How can I allocate a 2D array using double pointers?

[2] http://www.eng.cam.ac.uk/help/tpl/languages/C/teaching_C/node52.html

回答

2

第一malloc和所述的memcpy是不必要的,因爲你必須在ptr_array[0]容易訪問原始數據陣列。您不需要知道舊的大小,因爲realloc應該記得它在地址處分配了多少,並移動了正確的數據量。

這樣的事情應該工作。

double ** 
reallocate_double_array (double **ptr_array, int count_row_new, int count_col) 
{ 
    int i; 
    int new_size = count_row_new * count_col; 

    double *data = ptr_array[0]; 
    data = realloc (data, new_size * sizeof (double)); 

    free (ptr_array); 

    ptr_array = calloc (count_row_new, sizeof (double *)); 

    for (i = 0; i < count_row_new; i++) 
    ptr_array[i] = data + (i * count_col); 

    return ptr_array; 
} 
+0

非常感謝。這是正確的,並且運作良好。 – coastal 2011-03-04 20:05:13