2016-12-04 67 views
0

我想从字符串中替换字符(例如第二个字符)。 我的代码有什么问题?它可以编译,但不是做我所需要的,它给我一个分段错误。谢谢!通过替换字符串的字母在C中的分段错误

#define _XOPEN_SOURCE 
#include <unistd.h> 
#include <stdio.h> 
#include <cs50.h> 
#include <string.h> 

int main (int argc, string argv[]) 
{ 
    string key="abcd"; 
    key[1]='f'; 
} 

并经过编译我的代码

~/workspace/pset2/crack/ $ clang -ggdb3 -O0 -std=c11 -Wall -Werror -Wshadow bug.c -lcrypt -lcs50 -lm -o bug 
~/workspace/pset2/crack/ $ ./bug 
Segmentation fault 

回答

0

只能修改内存,在堆或堆栈,你"abcd"有所谓的字符串文字和所属的程序的只读存储器空间,它不能被修改的地方是(不管它是否在任何体面的操作系统下运行)。

它被放置在那里的原因是因为string基本上只是一个char *指针,它将指向任何内存空间并且不在乎它是否在只读空间。 (不要与C++ std::string混淆)。

为了使它可以修改,你必须告诉C它不是一个指针,而是一个数组。

char key[] = "abcd"; 

现在C会将这个字符串放在堆栈中,您可以随意修改它。

0
string key="abcd"; 

string基本上是char *key是字符串文字。您尝试修改它,因此分段错误。

0

我没有看到名称string的定义,但我认为它是类似于char *

因此,在此声明

string key="abcd"; 

那里被宣布为指向字符串文字。

字符串文字在C中未修改,任何修改字符串文字的尝试都会导致未定义的行为。

从C标准(6.4.5字符串文本)

7这些阵列是否是不同的条件是它们的 元素具有适当的值是不确定的。 如果程序尝试 修改这样一个数组,行为是未定义的。

+0

'string'是从一个叫做'cs50'库一个typedef,你得到它的权利 - 这只是'字符*'。显然这个库在哈佛的入门课程中用于从键盘读取。这听起来很有用,但是这个typedef实际上不应该存在。 – giusti

+0

@giusti感谢您的信息。:) –

0

这是因为"abcd"并未真正复制到您的key变量中。 相反,key是一个指向这个常量字符串的指针。

如果你希望能够修改它,你可以这样做:

int main (int argc, string argv[]) 
{ 
    char key[] = { "some string" }; 
    key[1]='f'; 
}