我有这个简单的程序,它可以正常工作。
#include<stdio.h>
int main(int argc, char *argv[]) {
int mystrlen(char *s);
char s[6] = "ABCDEF";
printf("%d", mystrlen(s)); // print 6
}
int mystrlen(char *s) {
char *p=s; /*Assigning the starting value to p */
while(*s != '\0') {
s = s + 1;
}
return s-p;
}
我将做的唯一更改是int main(int argc, char *argv[])
而不是int main(void)
,我将使用#include<stdio.h>
int main(void)
{
int mystrlen(char *s);
char s[6]="ABCDEF";
printf("%d",mystrlen(s)); // prints 8 !!
}
int mystrlen(char *s) {
char *p=s; /*Assigning the starting value to p */
while(*s != '\0') {
s = s + 1;
}
return s-p;
}
,我不会发送任何命令行参数。
现在,同样的程序对我来说完全行为不端!
{{1}}
任何人都可以解释为什么会这样吗?这是我期望在程序中出错的最后一件事。这是编译器依赖的行为吗? FWIW,我正在使用gcc
答案 0 :(得分:6)
未定义的行为:您没有为null终止符分配空间。您应该在编译器中启用警告,这应该记住这一点。
答案 1 :(得分:3)
您的问题在于char s[6]="ABCDEF";
声明。 null终结符没有空间,这是所有标准库字符串函数(以及函数mystrlen
)所需要的。
请改用char s[]="ABCDEF";
。在这样做时,会自动为您添加空终止符 - 这就是引用文字的工作方式:将结束引用视为包含隐式\0
。此外,C将为您计算数组的大小,因此无需指定。
正式程序的行为目前未定义。它不仅依赖于编译器,而且依赖于任何东西。
答案 2 :(得分:2)
这将是一个未定义的行为,因为您的源数组s
没有足够的空间来终止null,即\0
。启用编译器警告。
您可以像
一样更改数组char s[7]="ABCDEF";
来自C99标准
字符类型数组可以由字符串初始化 文字,可选择括在括号中。连续的人物 字符串文字(包括终止空字符if) 有空间或者如果数组的大小未知)初始化 数组的元素