关于C ++中的移位操作技巧?

时间:2014-02-12 01:52:36

标签: c++

当我阅读Google Protocol Buffers中的代码时,我发现了如下混淆代码。

1 < 2 ? (void)0 : cout << "hi" << endl;

关键是字符串“hi”将通过左移位运算符管理NULL。结果,什么也没发生。这意味着这是正确的语法代码。

我尝试了一些不同的代码,如下所示。

(void)0 << "hi" << endl;

当然,它没有用。

最后,我尝试了这段代码。

string tmp;
cin >> (1 < 2 ? 0 : tmp);

它已编译但在运行时崩溃。 (如果符号反向更改但输入未存储在tmp中,则有效。)

是否有人可以告诉我第一种情况会发生什么? (在编译器或低级别,如果可能)

3 个答案:

答案 0 :(得分:5)

你误解了它,1 < 2 ? (void)0 : cout << "hi" << endl;转换为:

if(1 < 2) {
    (void)0; //do nothing
} else {
    cout << "hi" << endl;
}

condition ? true-state : false-state;被称为ternary operator,它绝对与<<无关。

答案 1 :(得分:3)

<< has higher precedence than ?:,所以:

 1 < 2 ? (void)0 : cout << "hi" << endl;

实际上相当于:

(1 < 2) ? (void)0 : (cout << "hi" << endl);

到:

 ((1 < 2 ? (void)0 : cout)) << "hi" << endl;

(当然,如果condition ? then_expression : else_expresion为真,else_expression根本不会评估condition。)

答案 2 :(得分:1)

1 < 2 ? (void)0 : cout << "hi" << endl;

其他答案指出,运算符优先级给出了与您假设的不同的含义,因此上述内容相当于:

(1 < 2)
    ? (void)0
    : (cout << "hi" << endl);

但它仍然是非法的。

如果?:条件运算符的第二个或第三个操作数的类型为void,则另一个必须属于void 的类型必须是一个throw-expression。

将第三个操作数转换为void将解决该问题:

1 < 2 ? (void)0 : (void)(cout << "hi" << endl);

如果您可以更新问题以显示您所询问的完全代码,我们可以更好地解释它。

看到出现这种情况的背景也很有趣。就其本身而言,它可以作为if声明更加清晰。