加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 百科 > 正文

c – 使用memcpy()复制包含指针的结构是否可以?

发布时间:2020-12-16 10:32:35 所属栏目:百科 来源:网络整理
导读:前几天我在考虑这件事,如果这是一个坏主意我很好奇…… 可以说有一个结构包含一个指向字符串数组的指针. memcpy()会复制下面示例中的’name’数组指针吗? 编辑:此示例中无法访问std. struct charMap{ unsigned char * name; unsigned char id; };typedef s
前几天我在考虑这件事,如果这是一个坏主意我很好奇……
可以说有一个结构包含一个指向字符串数组的指针.
memcpy()会复制下面示例中的’name’数组指针吗?
编辑:此示例中无法访问std.

struct charMap
{ 
  unsigned char * name;   
  unsigned char id;       
};
typedef struct charMap CharMapT;

class ABC
{
  public:
  ABC(){}
  void Function();
  CharMapT* structList;
}

void ABC::Function ()
{
  CharMapT list[] = 
  {
    {"NAME1",1},{"NAME2",2},{"NAME3",3}
  };

  structList = new CharMapT[sizeof(list)];
  memcpy(structList,&list,sizeof(list));
}

解决方法

在我们将要讨论的代码中存在几个错误,我将首先讨论这个错误,然后是指针与数组的股票dia骂.

struct charMap
{ 
  unsigned int * name;   
  unsigned int id;       
};
typedef struct charMap CharMapT;

这声明了一种结构类型,其中包含指向unsigned int的指针作为第一个成员(name),int作为第二个成员(id).在具有默认字节打包的32位系统上,这将是8字节宽(32位指针= 4字节,32位符号int = 4字节).如果这是一个64位机器,指针将是8字节宽,int仍然可能是32位宽,使结构大小为12字节.

可疑代码

void ABC::Function ()
{
  CharMapT list[] = 
  {
    {"NAME1",sizeof(list));
}

这将分配CharMapT结构的动态数组.多少?比你想象的更多. sizeof(list)将返回list []数组的字节数.由于CharMapT结构宽度为8个字节(见上文),因此这将是3 * 8或24个CharMapT项目(如果使用64位指针则为36项).

然后我们将memcpy()从列表中的24个字节(或36个字节)(& in& list是不必要的)到新分配的内存.这将复制3个CharMapT结构,留下我们分配的其他21个(超出其初始默认构造).

注意:您正在将const char *初始化为声明为unsigned int *的字段,因此如果这甚至编译了基本数据类型将是不同的.假设您修改了结构并将指针类型更改为const char *,则const数据段中某处的静态字符串常量地址(“NAME”常量的地址)将分配给structList中元素的指针变量[0] .name,structList [2] .name和structList [3] .name分别.

这不会复制指向的数据.它只会复制指针值.如果你想要数据的副本,那么你必须对它们进行原始分配(malloc,new,等等).

更好的是,使用std :: vector< CharMapT>,使用std :: string作为CharMapT :: name,并使用std :: copy()复制源(甚至直接赋值).

我希望能解释你在寻找什么.

指针与阵列Diatribe

切勿将指针与数组混淆.指针是保存地址的变量.就像一个int变量保存一个整数值,或者一个char变量保存一个字符类型,指针中保存的值就是一个地址

数组是不同的.它也是一个变量(显然),但它不能是l值,几乎每个地方通常都会使用转换.从概念上讲,转换会产生一个指向数组数据类型的临时指针,并保存第一个元素的地址.有时候这个概念不会发生(例如应用地址运算符).

void foo(const char * p)
{
}

char ar[] = "Hello,World!";
foo(ar); // passes 'ar',converted to `char*`,into foo. 
         // the parameter p in foo will *hold* this address

或这个:

char ar[] = "Goodbye,World!";
const char *p = ar;  // ok. p now holds the address of first element in ar
++p;                 // ok. address in `p` changed to address (ar+1)

但不是这个:

char ar[] = "Goodbye,World!";
++ar; //  error. nothing to increment.

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读