Neu*_*ino 104 c++ if-statement compilation variable-declaration
这里发生了什么?
if(int a = Func1())
{
// Works.
}
if((int a = Func1()))
{
// Fails to compile.
}
if((int a = Func1())
&& (int b = Func2()))
)
{
// Do stuff with a and b.
// This is what I'd really like to be able to do.
}
Run Code Online (Sandbox Code Playgroud)
2003标准中的6.4.3节阐述了在选择语句条件中声明的变量如何具有延伸到由条件控制的子语句末尾的范围.但是我没有看到它在什么地方说不能在括号内加上括号,也没有说明每种条件只有一个声明.
即使在需要条件中只有一个声明的情况下,这种限制也很烦人.考虑一下.
bool a = false, b = true;
if(bool x = a || b)
{
}
Run Code Online (Sandbox Code Playgroud)
如果我想在x设置为false的情况下输入'if"-body范围,则声明需要括号(因为赋值运算符的优先级低于逻辑OR),但由于括号不能使用,因此需要声明外部x身体,将声明泄露到比预期更大的范围.显然这个例子是微不足道的,但更现实的情况是a和b是函数返回需要测试的值
那么我想要做的是不符合标准,还是我的编译器只是破坏了我的球(VS2008)?
Jam*_*ton 104
我想你已经暗示过这个问题了.编译器应该如何处理这段代码?
if (!((1 == 0) && (bool a = false))) {
// what is "a" initialized to?
Run Code Online (Sandbox Code Playgroud)
"&&"运算符是短路逻辑AND.这意味着如果第一部分(1==0)结果为假,那么第二部分(bool a = false)应该不被评估,因为已经知道最终答案将是假的.如果(bool a = false)没有评估,那么以后如何使用代码a呢?我们不会初始化变量并保持未定义吗?我们会将其初始化为默认值吗?如果数据类型是一个类并且这样做会产生不良副作用怎么办?如果bool您没有使用类而且它没有默认构造函数,那么用户必须提供参数 - 那么我们该怎么办?
这是另一个例子:
class Test {
public:
// note that no default constructor is provided and user MUST
// provide some value for parameter "p"
Test(int p);
}
if (!((1 == 0) && (Test a = Test(5)))) {
// now what do we do?! what is "a" set to?
Run Code Online (Sandbox Code Playgroud)
似乎你发现的限制似乎完全合理 - 它可以防止这些歧义发生.
Mik*_*our 93
if或while语句中的条件可以是表达式,也可以是单个变量声明(带初始化).
您的第二个和第三个示例既不是有效的表达式,也不是有效的声明,因为声明不能构成表达式的一部分.虽然像第三个例子那样编写代码会很有用,但是需要对语言语法进行重大更改.
我没有看到它在什么地方说不能在括号内加上括号,也没有说明每个条件只有一个声明.
6.4/1中的语法规范给出了以下条件:
condition:
expression
type-specifier-seq declarator = assignment-expression
Run Code Online (Sandbox Code Playgroud)
指定单个声明,没有括号或其他装饰.
fwy*_*ard 48
从C++ 17开始,您最终可能会尝试做什么:
if (int a = Func1(), b = Func2(); a && b)
{
// Do stuff with a and b.
}
Run Code Online (Sandbox Code Playgroud)
注意使用;而不是,分隔声明和实际条件.
cra*_*str 20
如果要将变量括在较窄的范围内,则可以始终使用其他变量 { }
//just use { and }
{
bool a = false, b = true;
if(bool x = a || b)
{
//...
}
}//a and b are out of scope
Run Code Online (Sandbox Code Playgroud)
Bo *_*son 18
最后一节已经有效,你只需要写一点略有不同:
if (int a = Func1())
{
if (int b = Func2())
{
// do stuff with a and b
}
}
Run Code Online (Sandbox Code Playgroud)