打印结果时出现未知符号

时间:2018-02-02 15:43:40

标签: c

我有两种方法可以达到同样的目的,第一种方式打印未知符号,第二种方式打印出我想要的。

第一种方式:

const char *constStr = "Hello world";
char *str = (char*) malloc(strlen(constStr) + 1), *p = str;
while (*constStr) {
    *p = *constStr;
    constStr++;
    p++;
}
printf("%s\n", str);
free(str);

结果:

第二种方式:

const char *constStr = "Hello world";
char *str = (char*) malloc(strlen(constStr) + 1);
for (int i = 0; i <= strlen(constStr); i++) {
    str[i] = constStr[i];
}
printf("%s\n", str);
free(str);

结果:

为什么第一种结果看起来很奇怪?

2 个答案:

答案 0 :(得分:1)

不,你没有null终止字符串。这是使用printf格式说明符将指针传递到%s中的非空终止char数组的未定义行为。

在循环之外制作*p=0。这将使null终止char数组。

第二种方式是打印,因为您复制了\0数组的strlen(constStr)索引中的<=。注意循环条件中的printf

那些奇怪的信件来自哪里?

根据%s进行思考。当它看到\0格式说明符时,它从作为参数提供给它的地址开始打印。现在什么时候停止?当它找到const char *constStr = "Hello world"; char *str = malloc(strlen(constStr) + 1), *p = str; while (*p++ = *constStr++); // here `\0` will be copied. printf("%s\n", str); free(str); 时。在这里它没有找到它,它读出你分配的内存。那些内存上的那些位模式被证明是那些不可打印的字符。这就是你所看到的。正确的方法是:

\0

使用琴弦时,请务必保持角落箱的清洁。我的意思是,检查{{1}}是否被复制等。当我们实现字符串例程时,这是一个很常见的问题。

答案 1 :(得分:1)

要修复第一个,请在字符串的末尾添加一个null:

const char *constStr = "Hello world";
char *str = (char*) malloc(strlen(constStr) + 1), *p = str;
while (*constStr) {
    *p = *constStr;
    constStr++;
    p++;
}

*p = '\0'; /* <-- HERE */

printf("%s\n", str);
free(str);

注意:您正在修改指向临时的指针 - 不推荐。使用与str相同的方法,使用另一个移位的指针。