std::cout声明是如何工作的
How does std::cout declaration work?
std::cout
对象在iostream
头文件中声明为
namespace std _GLIBCXX_VISIBILITY(default)
{
...
extern ostream cout;
...
}
从现在开始,我将去掉std::
前缀。
因此,据我所知,cout
"只是"ostream
类型的对象。我开始想知道为什么东西是用cout
打印到屏幕上,而不是用其他ostream
对象,所以我试图创建一个类型为ostream
的对象,但编译器不让我。事实上,ostream
只是basic_ostream<char>
的别名,并且该类型的默认构造函数是受保护的。好吧,我想。但后来我想知道:为什么宣布cout
是合法的呢?为什么不会产生编译错误?
extern
声明ostream
,例如
extern ostream os;
os << "Will you compile?n";
,这次我得到了os的未定义引用错误。然后问题就转移到下面:在其他地方是否有cout
的"定义"?如果有,在哪里?
我无法理解这个。我知道,出于性能和安全原因,标准头文件是以一种"神秘"的方式编写的,除非你完全掌握了这种语言(我仍然不太可能),否则并不总是容易阅读,但我想理解这一点。
谢谢。
我开始想知道为什么东西是用cout打印到屏幕上,而不是用其他ostream对象,
因为std::cout
使用了一个与stdout
设备相关联的流缓冲区
所以我尝试创建一个ostream类型的对象,但是编译器不允许。事实上,ostream只是basic_ostream的别名,该类型的默认构造函数是受保护的。好吧,我想。但后来我想知道:为什么一开始就宣布结婚是合法的?为什么不会产生编译错误?
因为它是声明,而不是定义,所以它不调用任何构造函数。也许你应该读一读extern
在声明中的含义。
带有extern
的声明只是表示在程序的其他地方定义了一个类型为ostream
并称为cout
的对象。由于您实际上没有提供任何这样的定义,因此您会得到链接器错误。
要近似模拟std::cout
,您可以在某些.cpp
文件中这样做:
namespace {
std::ofstream fake_cout("/dev/stdout");
}
std::ostream cout(fake_cout.rdbuf());
创建一个写入/dev/stdout
的fstream
,然后将ostream
(称为cout
)与其流缓冲区关联。
这并不是对真正的std::cout
的一个很好的模拟,因为它不能确保在任何其他全局变量尝试使用它之前对流进行初始化,而真正的全局变量是这样做的。
在其他地方有cout的"定义"吗?如果有,在哪里?
是的,在标准c++库的libstdc++实现中有cout
的定义。这个定义在标准c++中是无效的。没关系,因为标准c++库的实现不一定要用标准c++编写,它只需要以实现的其余部分能够理解的方式编写即可。
- C++ Setter/Getter,cout 工作,printf 失败
- C++代码停止工作错误使用cout内部函数
- 错误:三元运算符无法在对象中正常工作"cout"
- cout 在我的程序上无法正常工作,有人可以帮助我吗?
- 无法让我了解 cin.get 和 cout 在这里的工作方式
- CIN 和 COUT 如何在以下程序中工作
- 简单的cin cout代码由"build and run"运行,但从bin/debug/x开始工作.exe
- cout 似乎在矢量迭代器C++中无法正常工作
- 在 Cout << "hello" << endl 中删除 endl 后,我的C++程序停止工作
- 为什么 cout.put() 在流中无法正常工作?
- 编写一个简单的函数,其工作方式与"std::cout"类似,但在末尾添加换行符
- cout在获取行输入(getline)后无法在c++中工作
- 这个cout将如何工作
- Cin 和 Cout 对象如何在循环中工作
- cout在cin之前没有在visual studio社区C++中工作
- cout 的<<运算符如何根据运算符优先级工作
- MyFile.open 无法正常工作,COUT 不显示数据
- std::cout声明是如何工作的
- c++ streamsize prec = cout.precision(3) -它是如何工作的
- 运算符重载("<<"):为什么"cout"不能正常工作?