我刚从电子书开始学习C ++ 我的代码没有任何错误,但我确实有一个问题 本书使用以下代码总结两个数字:
#include <iostream>
int main()
{
std::cout << "Enter two numbers:" << std::endl;
int v1 = 0, v2 = 0;
std::cin >> v1 >> v2;
std::cout << "The sum of " << v1 << " and " << v2
<< " is " << v1 + v2 << std::endl;
return 0;
}
所以int v1 = 0,v2 = 0;
用于变量。
为什么他们被初始化为0?
答案 0 :(得分:22)
这是cargo cult programming。它不是有害的,但它在这里没有任何实际好处,而且很可能只是因为作者想要简化一个概念用于教学目的,或者因为他误解了某些东西。
这就是原因。
通常,所有变量应在声明后直接初始化。这可确保变量永远不会处于不确定状态。这使得控制流更简单,代码更容易推理,从而防止错误。
但这只有在我们能够用有意义的值初始化变量时才有意义 - 也就是说它后面要表示的值。在你的代码中,情况并非如此 - 相反,变量通过输入流得到它们后来的值(不幸的是,C ++不支持使用值初始化变量的简洁,规范的方式从输入中读取。)
正如@jrok所说,初始化表面上可以防止无效输入和代码中的后续错误。我说表面上是,因为那不是真的:我们用 - 0
初始化变量的值 - 在程序的上下文中也无效所以我们没有'实际上获得了任何东西。
Jack Aidley提出这个代码的真正原因是防止编译器警告。但是由于上面提到的原因,没有编译器应该在这里警告。事实上,即使在编译时启用了大量警告,GCC 也不会发出警告。也许其他编译器可以,但我会考虑这个警告噪音。
答案 1 :(得分:15)
int v1 = 0;
那叫做初始化,这是一个很好的习惯。如果省略内置类型的初始值设定项,则其值被称为 indeterminate ,读取这样的值是非法的。
我们假设您这样做:
int v1;
std::cin >> v1;
std::cout << v1;
第二行中的输入操作可能会失败,例如,如果您输入字母而不是数字,则v1
将保持不变。没有检查输入是否成功以及v1
是否仍然未初始化,砰!您已经调用了未定义的行为,并且您可以完全放弃编译器来执行它想要的任何操作。
在您发布的代码中,v1
和v2
已初始化,即使输入失败,您也至少会获得某些结果并且定义明确的行为。
那就是说,不检查输入是否成功是一个逻辑错误。毕竟,0
是一个有效的输入可能性,如果没有额外的检查,就无法判断用户输入的内容是什么。
最简单的方法是在布尔上下文中使用输入表达式,在if
条件内:
if (std::cin >> v1 >> v2) {
// good, use v1 and v2
} else {
// bad input, we can't
// rely on v1 and v2 to
// have meaninful value here
}
Streams可隐式转换为bool
,如果没有设置错误标记,则会评估为true
和false
。
完成上述检查后几乎不需要初始化,因为如果输入失败,我们永远不会触及v1
和v2
。
答案 2 :(得分:13)
这是一种常见的做法,但在这个例子中,这是一个没有充分考虑错误处理的解决方法。如果您不初始化它们,那么您可以获得无效值的合理化仅在您无需检查输入是否成功时才有意义。代码不会检查输入是否成功,因此它存在致命缺陷。没有多少其他不需要的初始化可以解决这个问题。
std::cin >> v1 >> v2;
if (std::cin)
std::cout << "The sum of " << v1 << " and " << v2
<< " is " << v1 + v2 << std::endl;
else
std::cout << "Bogus input\n";
答案 3 :(得分:1)
通常的做法是在定义变量时为变量设置值。 有时,当您尝试使用未使用值初始化的变量进行操作时,会出现错误。
但是在你的例子中,它并不重要,因为你用cin read设置了一个值。
答案 4 :(得分:0)
虽然其他答案是正确的,但我不认为它们可能是这些变量初始化为零的实际原因。
相反,我强烈怀疑原因是:如果不是,大多数编译器会发出关于使用未初始化变量的警告。我认为这里的初始化主要是或者纯粹是为了抑制发出警告。
答案 5 :(得分:-1)
这是常见做法的一部分。
最好将值初始化为变量以使其具有完整性。