【问题标题】:Unable to alter a character in string literal Via pointer [duplicate]无法通过指针更改字符串文字中的字符[重复]
【发布时间】:2014-09-02 14:26:29
【问题描述】:

我正在尝试使用指针分配一个字符,但它不这样做。

有人能解释一下为什么以下程序停止工作吗?

#include <string.h>

int main(void) {
  char *s = "modifying...";
  // char s2[] = {'m','o','d','i','f','y','i','n','g','.','.','.',NULL};
  // s = s2;
  puts(s);
  *s = 'M'; // Here the program stops working
  puts(s);
  return 0;
}

【问题讨论】:

  • 简短的回答是“修改...”将存储在只读存储器中。
  • 是的,一个答案。
  • “无法更改字符串文字中的字符” - 完全正确。您不能修改字符串文字。

标签: c pointers


【解决方案1】:

你不能那样改变字符串字面量。

https://stackoverflow.com/a/17507772/234307

“C 字符串文字创建一个匿名的 char 数组。任何修改该数组的尝试都有未定义的行为。” - 基思汤普森

【讨论】:

  • 如果您可以通过链接到另一个问题的答案来回答问题,这表明也许第一个问题应该作为重复而不是回答而关闭。
【解决方案2】:

尽管 C 中的字符串文字具有非常量字符数组的类型,但它们是不可变的。您不能更改字符串文字。 改为使用

char s[] = "modifying...";

【讨论】:

  • Pedantry:不能保证它们是不可变的。 C 标准不需要它,至少 gcc 可以选择使它们可写。
  • @hyde C 标准中有明确写到“相同的注意事项适用于字符串文字中序列的每个元素,就好像它在整数字符.constant 中一样”
  • 快速谷歌搜索似乎表明,这只是指语法,而不是实际数据。如果它引用数据,你怎么能在字符串文字中获取元素的地址,如果它真的是获取整数 char 常量的地址?
  • @hyde 对不起。正确的引用是“如果程序尝试修改这样的数组,则行为未定义。”
【解决方案3】:

字符串文字本身位于函数外部的内存中。您想要做的是为可修改的字符串分配一个缓冲区...

char *pszLiteral = "literal";
char *pszBuffer = (char *)malloc(strlen(pszLiteral) + 1);
strcpy(pszBuffer, pszLiteral); // copy the literal value located at pszLiteral to the buffer pszBuffer, which is modifiable (located on heap)
*pszBuffer = 'L'; // or pszBuffer[0] = 'L';
puts(pszBuffer);
free(pszBuffer);

或者您可以使用位于堆栈而不是堆上的静态缓冲区

char *pszLiteral = "literal";
char pszLocal[20];
strcpy(pszLocal, pszLiteral);
*pszLocal = 'L'; // or pszLocal[0] = 'L';
puts(pszLocal);

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2023-04-01
    • 2016-06-19
    • 1970-01-01
    • 1970-01-01
    • 2016-10-21
    • 2021-05-14
    • 1970-01-01
    相关资源
    最近更新 更多