意外的 C 输出
unexpected C output
这个程序...
int main(void)
{
printf("CASSIUS"+'');
return 0;
}
...编译成功,但是:
**Warning** main.c:13:8: warning: format not a string literal and no format arguments [-Wformat-security]
printf("CASSIUS"+'');
你能解释一下为什么输出是0吗?
在本次通话中
printf("CASSIUS"+'');
这里用到了指针运算。字符串文字“CASSIUS”被转换为指向其第一个元素的指针,该元素添加了十进制等于 9 的整数字符常量。结果指针指向字符串文字之外。所以程序有未定义的行为。
请记住,八进制整数字符常量“\11”的值等同于转义序列“\t”。
因此整个表达式没有意义。
例如,如果您想在输出中附加换行符,您可以编写
printf("CASSIUS" "");
或
printf("CASSIUS" "\n");
或者只是
printf("CASSIUS\n");
注意,根据C标准,不带参数的函数main应该这样定义
int main( void )
常量 ''
的值为 9。字符串文字 "CASSIUS"
是 char
的数组长度 8(包括空终止符)。表达式 "CASSIUS"+''
指向字符串文字的第 9 个元素(从 0 开始计数),它比数组的最后一个元素(索引为 7)多两个元素。这是一个“指针溢出”,它是 未定义行为 .1 未定义行为的一个示例,当 printf
函数取消引用它时也会发生无效指针。
―
1 允许构造一个指针值指向数组最后一个元素之后的一个元素而不会指针溢出,尽管取消引用这样的指针也会导致未定义的行为。
来自 GCC warning: format not a string literal and no format arguments [-Wformat-security]
的警告是因为 GCC 无法检查 printf
格式说明符参数是否与其他 printf
参数一致,除非格式说明符参数指定为字符串文字(或作为字符串文字的串联)。
这个程序...
int main(void)
{
printf("CASSIUS"+'');
return 0;
}
...编译成功,但是:
**Warning** main.c:13:8: warning: format not a string literal and no format arguments [-Wformat-security] printf("CASSIUS"+'');
你能解释一下为什么输出是0吗?
在本次通话中
printf("CASSIUS"+'');
这里用到了指针运算。字符串文字“CASSIUS”被转换为指向其第一个元素的指针,该元素添加了十进制等于 9 的整数字符常量。结果指针指向字符串文字之外。所以程序有未定义的行为。
请记住,八进制整数字符常量“\11”的值等同于转义序列“\t”。
因此整个表达式没有意义。
例如,如果您想在输出中附加换行符,您可以编写
printf("CASSIUS" "");
或
printf("CASSIUS" "\n");
或者只是
printf("CASSIUS\n");
注意,根据C标准,不带参数的函数main应该这样定义
int main( void )
常量 ''
的值为 9。字符串文字 "CASSIUS"
是 char
的数组长度 8(包括空终止符)。表达式 "CASSIUS"+''
指向字符串文字的第 9 个元素(从 0 开始计数),它比数组的最后一个元素(索引为 7)多两个元素。这是一个“指针溢出”,它是 未定义行为 .1 未定义行为的一个示例,当 printf
函数取消引用它时也会发生无效指针。
―
1 允许构造一个指针值指向数组最后一个元素之后的一个元素而不会指针溢出,尽管取消引用这样的指针也会导致未定义的行为。
来自 GCC warning: format not a string literal and no format arguments [-Wformat-security]
的警告是因为 GCC 无法检查 printf
格式说明符参数是否与其他 printf
参数一致,除非格式说明符参数指定为字符串文字(或作为字符串文字的串联)。