简体   繁体   English

混合std :: cout的奇怪输出

[英]Strange outputs of mixed up std::cout

C++'s std::cout seems to be an interesting thing. C ++的std :: cout似乎很有趣。 I tried the following program on my C++ compiler today: 我今天在C ++编译器上尝试了以下程序:

cout<<"!"<<"@"<<endl;
cout<<"!"<<cout<<"@"<<endl;
cout<<"!"<<(cout<<"@")<<endl;

And the outputs are rather curious: 输出非常奇怪:

!@
!0x601068@
@!0x601068

The first line is pedestrian; 第一行是行人;第二行是行人。 the second is understandable; 第二个是可以理解的; however, the third line is beyond my knowledge. 但是,第三行是我所不知道的。 Could someone explain the output? 有人可以解释输出吗? Thank you guys all in advance! 谢谢大家!

Ziyao Wei 子耀伟

This line: 这行:

cout<<"!"<<(cout<<"@")<<endl;

It is first executing: 它首先执行:

(cout << "@")

Note: It could have executed something else first, but the compiler optimized this sub-expression and found it could move this to the start of the statement without breaking any constraints. 注意:它可能首先执行了其他操作,但是编译器优化了该子表达式,发现它可以将其移动到语句的开头而不会破坏任何约束。

The result of this expression is a stream (cout). 该表达式的结果是流(cout)。 So the resulting expression is: 因此,结果表达式为:

cout<<"!"<< cout <<endl;

This results in: 结果是:

@!<pointer>

The parenthes affect the order of evaluation here as in any other expression (<< is an operator). 括号会像其他表达式一样影响此处的求值顺序(<<是运算符)。 Because the expression has side-effects , those side-effects occur in the same order as the expression evaluation. 因为该表达式具有副作用 ,所以这些副作用的发生顺序与表达式评估的顺序相同。

This third line illustrates the syntactic sugar that is the insertion operator. 第三行说明了作为插入运算符的语法糖。

Essentially the (cout<<"@") expression is evaluated first, resulting in the @ , which returns the stream cout itself. 本质上,首先计算(cout<<"@")表达式,导致@ ,它返回流cout本身。

Its only then that the ! 只有这样! first, followed by the expression is sent to cout . 首先,将表达式发送到cout

Its equivalent to: 其等效于:

operator<<( operator<<( operator<<(cout,"!"), ( operator<<(cout,"@") ) ), endl);
                                                ^------------------^

The highlighted section is an expression which has to be evaluated before any functions are called. 突出显示的部分是一个表达式,必须在调用任何函数之前对其求值。

My supposition -- the parentheses in the 3rd line make the cout<<"@" execute first, which puts the @ at the start of the line. 我的假设-第三行中的括号使cout<<"@"首先执行,这会将@放在行的开头。 Then the cout.operator<<("!") executes which puts the ! 然后执行cout.operator<<("!") ,将! in place. 到位。 And then the ostream that cout.operator<<("!") returns runs its operator<<() which is given the ostream that cout<<"@" returned, thus outputting the 0x601068 . 然后, cout.operator<<("!")返回的ostream运行其operator<<() ,该operator<<()被赋予cout<<"@"返回的ostream ,从而输出0x601068

If you understand the second line, why does the third confuse you? 如果您理解第二行,那么为什么第三行会使您感到困惑?

First of all, the expression in the parentheses is evaluated (but the order of evaluation is unspecified), thus @ is wrote on the standard output; 首先,对括号中的表达式进行求值(但求值顺序未指定),因此@会写在标准输出上; such expression returns a reference to cout , as happens always with insertion operators, since otherwise they couldn't be chained. 此类表达式返回对cout的引用,就像插入操作符总是会发生的那样,因为否则它们将无法链接。

Now that this part of the expression is evaluated, everything proceeds as normal: what is on the line is wrote from left to right: first the ! 现在已经评估了表达式的这一部分,一切都照常进行:从左到右依次写出行中的内容:首先是! , then the value returned from the expression in the parentheses (ie the reference to cout and then the endl . ,然后从括号中的表达式返回的值(即对cout的引用,然后对endl的引用)。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM