许多C ++书籍都包含这样的示例代码...
std::cout << "Test line" << std::endl;
...所以我也总是这样做。但是,我已经从工作的开发人员那里看到了很多这样的代码:
std::cout << "Test line\n";
是否有技术上的理由要优先于另一个,还是仅仅是编码风格的问题?
'\n'
。
许多C ++书籍都包含这样的示例代码...
std::cout << "Test line" << std::endl;
...所以我也总是这样做。但是,我已经从工作的开发人员那里看到了很多这样的代码:
std::cout << "Test line\n";
是否有技术上的理由要优先于另一个,还是仅仅是编码风格的问题?
'\n'
。
Answers:
假设文件以文本模式打开,那么行尾字符的变化并不重要,除非您要求输入二进制文件,否则这就是您得到的。编译后的程序将为系统编译出正确的东西。
唯一的区别是std::endl
刷新输出缓冲区,'\n'
但不刷新。如果您不希望频繁刷新缓冲区,请使用'\n'
。如果这样做(例如,如果要获取所有输出,并且程序不稳定),请使用std::endl
。
::std::cerr
代替,::std::cout
因为每个输出操作都对它进行无缓冲和刷新。
stderr
是“错误”。相反,如果需要,它用于带外诊断消息。应该可以说./prog > file
和存储真正的程序有效负载,但是即使在正常交互中,程序也可能希望输出更多的状态信息。
差异可以通过以下方式说明:
std::cout << std::endl;
相当于
std::cout << '\n' << std::flush;
所以,
std::endl
如果要强制立即刷新到输出。\n
如果您担心性能,请使用(如果使用<<
运算符,则可能不是这种情况)。我\n
在大多数行上使用。
然后使用std::endl
在段落的末尾(但这只是一种习惯,通常不是必需的)。
与其他主张相反,\n
仅当流将要到达文件(std::cin
并且std::cout
是特殊但仍是文件(或类似文件))时,才将字符映射到正确的平台行尾。
cout
它与绑定在一起cin
,这意味着,如果您从读取输入cin
,cout
则将首先刷新。但是,如果您想显示进度条或其他内容而不从中读取cin
,那么可以肯定,刷新很有用。
operator<<
不是性能表现,或者还有什么替代性能的表现?请为我指出一些材料,以进一步理解这一点。
sync_with_stdio(false)
不同步,并且不要连续刷新输出。让图书馆弄清楚什么时候去做。stackoverflow.com/a/1926432/14065
如果要使用该函数,则意味着存在另一个函数调用 std::endl
a) std::cout << "Hello\n";
b) std::cout << "Hello" << std::endl;
a)<<
一次致电接线员。
b)<<
两次呼叫接线员。
std::cout << "Hello" << "\n";
呢
<<
的情况下,对a的调用也将为2 ,因此我不会声称需要一个或两个<<
(或两个函数调用)\n
和之间的区别endl
。
我记得在标准中对此有所了解,所以这里是:
请参阅C11标准,该标准定义了标准流的行为,因为C ++程序与CRT接口,因此C11标准应在此处管理刷新策略。
ISO / IEC 9899:201x
7.21.3§7
在程序启动时,预定义了三个文本流,无需显式打开它们-标准输入(用于读取常规输入),标准输出(用于写入常规输出)和标准错误(用于写入诊断输出)。最初打开时,标准错误流未完全缓冲;当且仅当可以确定该流不引用交互式设备时,标准输入流和标准输出流才被完全缓冲。
7.21.3§3
当流没有缓冲时,字符应尽快从源或目的地出现。否则,字符可能会作为块被累积并传输到主机环境或从主机环境传输。当流被完全缓冲时,打算在填充缓冲区时将字符作为块与主机环境进行传输。当流被行缓冲时,字符将在遇到换行符时作为块与主机环境进行传输。此外,当填充缓冲区,在无缓冲流上请求输入或在需要从主机环境传输字符的行缓冲流上请求输入时,打算将字符作为块传输到主机环境。 。
这意味着,std::cout
和std::cin
是完全缓冲当且仅当他们所指的非交互设备。换句话说,如果将stdout连接到终端,则行为上没有差异。
但是,如果std::cout.sync_with_stdio(false)
被调用,那么'\n'
即使是交互式设备也不会引起刷新。否则'\n'
等效于std::endl
除非管道到文件:std :: endl上的c ++ ref。
没什么大不了的,但是endl在boost :: lambda中不起作用。
(cout<<_1<<endl)(3); //error
(cout<<_1<<"\n")(3); //OK , prints 3
如果您使用Qt和endl
,则可能会意外地使用不正确的endl
结果,从而给您带来非常令人惊讶的结果。请参见以下代码段:
#include <iostream>
#include <QtCore/QtCore>
#include <QtGui/QtGui>
// notice that there is no "using namespace std;"
int main(int argc, char** argv)
{
QApplication qapp(argc,argv);
QMainWindow mw;
mw.show();
std::cout << "Finished Execution!" << endl;
// This prints something similar to: "Finished Execution!67006AB4"
return qapp.exec();
}
请注意,我写的endl
不是std::endl
(本来是正确的),显然是endl
在qtextstream.h(它是QtCore的一部分)中定义了一个函数。
使用"\n"
而不是endl
完全回避任何潜在的名称空间问题。这也是一个很好的例子,为什么将符号放入全局名称空间(默认情况下像Qt一样)不是一个好主意。
using namespace std;
?:-)
using namespace std;
。这被认为是不良做法。请参阅为什么“使用名称空间标准”;被认为是不良做法?
我一直有只使用std :: endl的习惯,因为它很容易看到。
与参考这是一个只输出I / O操作器。
std::endl
在输出序列os中插入换行符,并通过调用os.put(os.widen('\n'))
后跟来刷新它os.flush()
。
何时使用:
该操纵器可用于立即产生一行输出,
例如
显示长时间运行的进程的输出时,可能会意外崩溃的多个线程的日志记录活动或程序的日志记录活动。
也
如果生成的进程执行任何屏幕I / O,则在调用std :: system之前也必须显式刷新std :: cout。在大多数其他常见的交互式I / O场景中,std :: endl与std :: cout一起使用时是多余的,因为任何来自std :: cin的输入,输出到std :: cerr或程序终止都会强制调用std :: cout .flush()。在某些来源的鼓励下,使用std :: endl代替'\ n'可能会大大降低输出性能。