[英]How to deep copy an array of char * in C++
我想執行char **的深層復制,但是我不知道如何分配內存/復制此數據類型。 這用於包含char **的類中的副本構造函數。 例如,假設我有以下代碼:
char ** arr1 = new char*[20];
arr1[0] = (char*)"This is index 1";
arr1[1] = (char*)"This is index 2";
char ** arr2;
如何將arr1的內容復制到arr2中? 任何幫助表示贊賞!
這是用於編程作業,老師希望所有字符串都存儲為char *,...
您可以告訴老師std::string
確實將字符串存儲為char*
。 如果他仍然不喜歡您使用std::string
那么您應該編寫自己的包裝程序,因為使用裸char*
是您編寫C時的工作,但不是在C ++中。 您應該寫一個:
struct my_string {
char* data;
... constructor, operator[], etc...
};
基本上,您不需要編寫比現在更多的代碼,但是您應該將其放在正確的位置(即,將其隱藏在漂亮的界面后面)。 當您考慮...時,您將立即看到它的好處。
...因此,字符串數組必須存儲為char *數組。
否。字符串數組是std::array<my_string>
(如果應該是動態的,則為std::vector<my_string>
)。 而且,如果您的老師堅持不使用std::vector
,那么您應該像對vector的字符串一樣進行操作(即將所有臟指針和內存內容封裝在一個地方)。
這似乎更像一個C問題,但這是一個示例:
char **AllocateAndDeepCopy(char **arr1, int arr1size)
{
unsigned int i;
char **arr2;
/* Allocate string array */
arr2 = new char*[arr1size];
/* Iterate array elements */
for (i=0; i<arr1size; i++) {
/* Allocate string */
arr2[i] = new char[strlen(arr1[i])+1];
/* Copy contents */
strcpy(arr2[i], arr1[i]);
}
return arr2;
}
稍后,您必須以這種方式釋放arr2
:
void DeallocateArr2(char **arr2, int size)
{
for (int i=0; i<size; i++) {
delete arr2[i];
}
delete arr2;
}
只需看一下http://en.cppreference.com/w/cpp/algorithm/copy ,深層副本就由* d_first ++ = * first ++;創建。
對於C ++教育的遺憾狀態,我只能搖頭。 我們有很長的路要走。 但是,既然這顯然是給定的,那么您能做的最好的事情是什么?
要復制這樣的C樣式數據結構,您在復制時要了解兩件事。 兩者都不是由C樣式數組固有提供的,因此您必須明確地跟蹤它們。
arr1
的容量 : 20 。 如果這不是編譯時間常數,則必須將其存儲並傳遞。 由於要實現一個復制ctor,這意味着將容量存儲在對象的非靜態成員變量中。 arr1
中使用的索引arr1
: 2 。 同上。 或者,確保所有未使用的索引都設置為nullptr
。 現在,您可以分配正確大小的arr2
,然后分配+ memcpy所有使用的索引。
但是, 無論如何 , 您的程序都會 arr1
,因為即使它們看起來相同,也無法將arr1
和arr2
視為相同。 使用過的arr1
索引永遠不能delete
d,因為它們包含指向字符文字的指針:它們絕不是new
d,並且位於只讀內存中。 另一方面,您絕對必須delete
arr2
的索引,因為它們是 new
d。
如果作業確實需要這種對const的殘酷無視,那么我會更進一步。 我將介紹另一個成員變量,一個布爾數組,該數組跟蹤char數組的哪些索引指向char文字,以及哪些是動態分配的。 復制期間,您現在擁有了所有必要的信息以進行memcpy或僅設置指針。 瘋? 絕對可以,但是整個任務都是這樣,這樣,瘋狂就至少可見,而不是隱藏在無辜的C風格演員之后。 順便說一句:那些應該是const_cast<char*>
,以明確發生了什么事情。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.