读入没有空终止符空间的数组是否合法?

  • 本文关键字:数组 是否 空间 终止 c++
  • 更新时间 :
  • 英文 :


当每个C字符串存储在C字符串变量中时,它都以null字符结束,并且这总是占用一个数组位置。

那么为什么这是合法的:

char name[3];
std::cin >> name;

当3个字母的单词";牛;是否输入到std::cin

为什么它允许这样做?

编译器无法知道您在运行时将给出什么输入,因此它不能说您将执行非法操作。如果输入符合数组,那么它是合法的。

以前的C++20:

程序的行为是未定义的。永远不要这样做。

由于C++20:

输入将被截断以适应数组,因此数组将包含字符串";co";。

这是允许的,因为内存管理留给了程序员。在这种情况下,错误发生在运行时,编译器不可能在编译时发现它。

你在这里得到的是一个未定义的行为,程序可能会崩溃,可以顺利进行,或者在未来出现一些奇怪的行为。

在这里,您很可能会将分配的内存溢出一个字节,该字节将存储在随后声明的变量的第一个字节中,或者存储在其他地址中,这些地址可能已经或可能尚未填充相关信息。

如果(例如(某个只读内存区域被覆盖,或者如果您将指令指针指向某个无效区域(再次,通过覆盖其在内存中的值(,您最终可能会经历执行中止

取决于您所说的"合法的";。就你的问题而言,并没有确切的含义。

根据标准(至少在C++20之前(,您的代码(如果提供了该输入(具有未定义的行为。当行为不明确时,任何可观察的结果都是允许的,不需要诊断。

特别是,不要求实现(编译器、主机系统或任何其他系统(诊断问题(例如发出错误消息(、采取预防措施(例如,在按下回车键之前因程序员输入"cow"而将其电死(或采取恢复措施(例如截断"co"的输入(。

标准允许这样做的原因是:;

  • 允许实现自由。例如,该标准允许但不要求主机系统因用户在程序中输入了错误的输入而对其进行电击,但并不能阻止邪恶的系统开发人员提供硬件和驱动程序支持来做到这一点
  • 技术上的不可行性或技术上的困难。在像您的代码这样的简单情况下,可能很容易检测到。但是,在更复杂的程序中(例如,您的代码隐藏在其他代码中(,可能无法识别问题。或者,这可能是可能的,但所花的时间比程序员愿意/能够花在等待上的时间要长得多

简而言之,C++标准不会对程序员造成太大的麻烦。程序员——不是标准,也不是编译器——负责避免未定义的行为,并负责是否有未定义行为的程序做了不希望的事情。

最新更新