C语言scanf读取字符串时宽度修饰符是否计入空终止符长度?
关于scanf %s宽度修饰符的问题解答
结论
第一种写法是正确的,你可以用它安全读取数组能存储的最大长度有效字符串:
char string[256]; scanf("%255s", string);
原理说明
scanf的%s格式符的宽度修饰符,指定的是最多读取的非空白字符数量,不包含末尾自动追加的空终止符\0。- 当你指定宽度为N时,
scanf最多读取N个字符,之后会自动写入1个\0作为字符串结束标记,总共会占用N+1字节的数组空间。 - 你的数组长度为256,预留1字节存储
\0的前提下,最多可容纳255个有效字符,因此宽度修饰符设为255是完全正确的。
错误写法风险
如果你写成scanf("%256s", string);,会触发缓冲区溢出:
- 此时
scanf会读取256个有效字符,再额外写入1个\0,总共向数组写入257字节内容,超出256字节的数组边界,属于未定义行为,可能导致程序崩溃、内存数据被篡改,甚至存在安全注入风险。
额外注意事项
- 示例代码中
char string[256]末尾缺少分号,实际编译运行时需要补全。 %s默认遇到空白字符就会停止读取,如果你需要读取包含空格的整行输入,更推荐使用fgets函数,安全性和可控性更高。
内容的提问来源于stack exchange,提问作者Shane1470
相关产品推荐
相关产品推荐

