2016-03-20 37 views
-1

我搜索了一個答案,但沒有設法找到一個。重新分配動態分配的結構

我有一個動態分配的結構,這意味着結構本身將被分配和它的一些成員。像:

typedef struct dataUse 
{ 
    char *num; 
    char *name; 
    char *position; 
    char *eMail; 
    float upload; 
    float download; 
} DataUse; 

DataUse *ptr = NULL; 

現在我擁有的功能重新分配內存*ptr,也爲​​,*position*eMailname,positioneMail的大小當然有所不同。

現在我明白了,重新分配某些內容會保留數據的原始地址並增加內存大小,或者如果它不能分配到同一空間,它將複製它的內容併爲該指針分配一個新地址。

現在在我的情況下,如果我重新分配我的struct*ptr),並希望增加其大小,後者開始,這意味着我的結構內容將被複制,新的地址將簽署,將會發生什麼​​,*position*email?我仍然可以通過ptr->num訪問它們和舊內容。我會有什麼樣的記憶力減退?

我只希望有人來驗證會發生什麼並解釋,如果我重新分配整個結構,它將如何在內存中查找。我看過,結構看起來像在內存中的樣子我已經閱讀了大量的帖子,但有時在添加更多指針並進入更深層次(例如使用雙指針)後會有點混亂。

然後會發生什麼,如果我用雙指針來做 - **ptr2來保持指向結構的指針,然後realloc **ptr2來保存更多的指針?

+1

什麼? '如果我重新分配我的結構' - 你的結構是固定大小的! –

+0

任何時候當你發現自己在問「它在內存中的效果如何」的時候,可以考慮在你的平臺上啓動一個調試器,並在其中執行一個調試器,並且實際上*這樣做*:I.e. *看着記憶*。實際上「看起來」的方式比其他任何地方都更好。 – WhozCraig

+0

@Martin James-我的結構不固定。我有一個函數,它會將內存添加到我的結構體ex:'void allocStruct(DataUse ** ptr){在此分配內存}'。 – Name

回答

1

如果我正確理解您的問題,您已分配DataUse的實例並將地址存儲在ptr中。現在你正在重新分配它。

指針存儲絕對地址,因此重新分配包含指針的結構體不會丟失數據。

因此,DataUse的實例位於內存中的某個地方,其地址存儲在ptr中。 num的數據位於其他地方,其地址存儲在num字段中DataUse。將DataUse的實例複製到另一個地方時,num字段也被複制,因此字符串num和name等的地址保持不變,並且仍位於num,name字段的新副本中。

您只需重新分配結構,即您存儲地址的位置已更改,但保存在num,name,...中的地址保持不變。

+0

「,但是...的地址......」,「地址*在......中保存」更準確。 *只要您更改包含它們的結構的地址,這些成員的地址就會改變。 – WhozCraig

+0

@songziming是的。我想分配* ptr來存儲更多的結構。所以,如果我理解正確,如果我的結構將被複制和添加內存,我可以訪問以前存儲的結構,它的成員通過* ptr? – Name

0

如果我們假設ptr[i]是有效的(例如至少i+1DataUse陣列先前已經使用malloc()分配),並且ptr點增加時,存儲器的使用realloc()尺寸,然後的ptr[i].num該地址將改變,如果ptr已更改,但ptr[i].num的值不會。

0

考慮下面的代碼片段:

DataUse *ptr= malloc(sizeof(DataUse)); // allocate non-zeroed memory 

上述分配內存爲您的結構。請注意,它沒有歸零,所以任何應該歸零的東西都必須由您歸零。

ptr->name= malloc(strlen(this_name)+1); 
strcpy(ptr->name, this_name); 

以上初始化爲name

free(ptr_name); 
ptr->name= malloc(strlen(new_name)+1); 
strcpy(ptr->name, new_name); 

以上在name中添加了一個新名稱。它首先釋放分配的內存。

char *tmpname= realloc(ptr->name, strlen(new_name)+1); 
if (tmpname) { 
    ptr->name= tmpname; 
    strcpy(ptr->name, new_name); 
} 
else printf("Out of memory); 

上述確實(約)相同,但使用realloc。請注意,如果以前未使用ptr->name,則必須爲零。