我今天知道cout和printf有缓冲区,据说缓冲区有点像堆栈,从右到左获取cout和printf的输出,然后从上到下将它们输出(到控制台或文件)。像这样,

a = 1; b = 2; c = 3;
cout<<a<<b<<c<<endl;
buffer:|3|2|1|<-   (take “<-” as a poniter)

output:|3|2|<-     (output 1)
        |3|<-       (output 2)
        |<-         (output 3)

然后我在下面写一段代码,

#include <iostream> 
using namespace std; 
int c = 6;
int f() 
{   
    c+=1; 
    return c; 
} 

int main() 
{ 
     int i = 0; 
     cout <<"i="<<i<<" i++="<<i++<<" i--="<<i--<<endl; 
     i = 0;
     printf("i=%d i++=%d i--=%d\n" , i , i++ ,i-- );

     cout<<f()<<" "<<f()<<" "<<f()<<endl; 
     c = 6;
     printf("%d %d %d\n" , f() , f() ,f() );
     system("pause");
     return 0; 
} 

在VS2005下,输出为

i=0 i++=-1 i--=0
i=0 i++=-1 i--=0
9 8 7
9 8 7

在 g++( (GCC) 3.4.2 (mingw-special)) 下,输出为,

i=0 i++=0 i--=1
i=0 i++=-1 i--=0
9 8 7
9 8 7

看起来缓冲区就像一个堆栈。然而,我读到 C++ 入门增强版 今天,据说 cout 从左到右工作,每次返回一个对象(cout),所以“这就是让你通过插入连接输出的功能”。但是从左到右的方式无法解释COUT <输出9 8 7现在我对Cout的缓冲区的工作方式感到困惑,有人可以帮助我吗?

有帮助吗?

解决方案

这不是错误,也不是任何与输出缓冲。

i--i++操作的执行顺序时,他们多次调用作为参数相同功能呼叫没有被定义。

要阐述(和可能正确的)的“序列点” Iraimbilanja的提及,所述cout版本等同于:

(((cout << a) << b) << c)

实际上,它实际上是三个单独的函数调用,其每个的参数,以便进行评估,即使它写入像一个单一语句。

<<操作者确实ostream& operator<<(ostream& os, int),所以写这的另一种方法是:

operator<< ( operator<< ( operator<< ( cout, a ), b ), c )

由于对于外调用它不是(AFAIK)中定义何种顺序的两个参数进行评估,这是完全可能的是,右侧的“c”的参数(或你的情况“i--”),以左手参数之前发生进行评价。

其他提示

输出:

printf("i=%d i++=%d i--=%d\n" , i , i++ ,i-- );

未指定。这是 C++ 的一个常见陷阱:参数评估顺序未指定。

cout 的情况则不然:它使用链式调用(序列点),而不是单个函数的参数,因此评估顺序从左到右定义良好。

编辑: David Thornley 指出上述代码的行为实际上是 不明确的.

如果可能尝试更新到GCC> = 4。我只是跑此上4.0.1和它执行只是饰面。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top