C- malloc会制作弦乐常数



首先,如果这是一个天真的问题,请原谅我;我只是一个试图学习的初学者。

我知道:

  char* a = "CD"; 

将字符串存储在读取仅记忆中;因此,对字符串的任何更改都是不可能的。(常数)

,但我确实知道使用malloc也是如此;

char* a = malloc(3*sizeof(char)) ;
a = "CD" ; 
a[0] = 'S' ; // even regular a = "MR"; does not work

我很困惑,我以为这是存储在 heap ...

为什么不能修改字符串?

a = "CD";char* a = "CD";完全相同:它将"CD"的地址存储在a中。呼叫返回的malloc的值被覆盖,并且分配的内存泄漏。

正确的方法是复制字符串:

strcpy(a, "CD");

您正在混淆指针和分配:

  • char*是在我们记忆中某个地方的某个炭的指针(它可能是堆也可能不是堆)
  • 常量记忆这样的字符串("CD"
  • 堆中的动态分配。

虽然指针可能指向常数或堆,但您可以执行相同的操作(例如:在示例中,用's'分配0)。这并不意味着它总是会在运行时起作用:它们可能对此有所保护。

更糟糕的例子:

char* a = "CD";
char* b = "ZZ";
strcpy(a, "EFGHAAAAAAAAAAAA"); // may fail with Segmentation fault
printf("a: %3s, b: %3sn", a, b); // may not work

使用 gcc(gentoo 7.3.0-r3 p1.4)7.3.0 ,并运行程序,它导致分段故障 strcpy。P>

您只能在分配的内存中使用strcpy

char* a = malloc(3*sizeof(char)) ;
strcpy(a, "EFGHAAAAAAAAAAAA"); // may fail with Segmentation fault
printf("a: '%s'n", a); // print a: 'EFGHAAAAAAAAAAAA'

这样做,您已经摆脱了界限:记忆最多可以存储3个字符,后者是

在这种情况下,您应该(总是?)而不是使用strncpy

char* a = malloc(3*sizeof(char));
strncpy(a, "EFGHAAAAAAAAAAAA", 3 );
a[2] = 0;

在旁边,您可能永远不要使用带有常数字符串的char*,而是const char*(编译器可能已经警告您,如果不使用-Wall):

const char* a = "CD" ; 
a[0] = 'S' ; // should not compile

否您只需将指针带有字符串的地址,而先前存储的maloced内存的地址就会丢失。

我知道:

char* a = "CD"; 

将字符串存储在只读内存中;因此,对字符串的任何更改都是不可能的。(常数)

取决于您如何看待它。C标准不会强制执行字符串文字最终仅读取内存。实际上,C标准甚至不需要系统仅具有读取内存。但是,如果您尝试修改字符串文字,则行为是不确定的。

C11标准的报价:

,如果它们的元素具有适当的值,则未指定这些数组是否不同。如果程序试图修改此类数组,则行为是未定义的。

https://port70.net/~nsz/c/c11/n1570.html#6.4.5p7

相关内容

  • 没有找到相关文章

最新更新