我有一个简单的程序,我有一个外部写的字符串(在这个snippit的情况下,它是用户创建的)。我正试图将其某些部分资本化。
我首先使用分隔符来定位它,并尝试使用toupper函数对其进行大写,但是我似乎正在使用segfaults来完成它。运行valgrind不会提供任何错误,只是说明:
Process terminating with default action of signal 11 (SIGSEGV)
==10180== Bad permissions for mapped region at address 0x4007B9
代码:
int main(void) {
char * test;
char * f;
char * s;
char * p;
test = "first:second:third:fourth:";
f = strtok(test,":");
for(p = f; *p; *p = toupper(*p), p++); //segfaults
printf("f is %s \n",f); //this should print "FIRST" as it should be capitalized
return 0;
}
答案 0 :(得分:2)
您不能在字符串文字上使用strtok()
,因为它会修改它的参数,并且您无法修改字符串文字。
你也不能在这个循环中修改它
for (p = f; *p; *p = toupper(*p), p++); //segfaults
你需要一个数组或一个动态分配的内存块,这两个内存都是可写的,你可以使用像这样的字符串文字初始化的数组
char array[] = "This is a string literal, you are not allowed to modify it";
/* Now the arest of the code could work but ... */
如果找不到您要查找的内容,还需要检查strtok()
NULL
的返回值。
使用malloc()
你也可以这样做
cosnt char *string_literal = "This is a sample string";
size_t length = strlen(string_literal);
char *buffer = malloc(length + 1);
if (buffer == NULL)
return -1; // Allocation failure.
memcpy(buffer, string_literal, length + 1);
// ^ copy the null terminator too
// Process your newly allocated copy here and,
free(buffer);
注意:关于原始代码
f = s = p = test = malloc(sizeof(char * ) * 10);
malloc()
不用作通用初始化函数,它用于获取可以在程序中使用的内存指针,可以从/向它读/写。当您使用malloc()
请求内存时,您需要在程序中使用特定的(通常精确的)字节数。
如果返回的指针不是NULL
,则可以使用它,如果出现错误或系统内存不足,它将返回NULL
。
您的代码存在一个主要问题,因为所有指针f
,s
,p
和test
都指向相同的内存地址,也因为您分配了任意大小这可能是你想要/不需要的那个。
当你free(f)
然后继续free(s)
时,你正在释放两次相同的指针而你实际上做的不止于此。在同一个poitner上调用free()
两次会调用未定义的行为。