繁体   English   中英

如何在C ++中深度复制char *数组

[英]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中使用的索引arr12 同上。 或者,确保所有未使用的索引都设置为nullptr

现在,您可以分配正确大小的arr2 ,然后分配+ memcpy所有使用的索引。

但是, 无论如何您的程序都会 arr1 ,因为即使它们看起来相同,也无法将arr1arr2视为相同。 使用过的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.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM