C++ printf 与 std::cout
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/4781819/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
printf vs. std::cout
提问by Zac Howland
Possible Duplicate:
Should I use printf in my C++ code?
可能的重复:
我应该在 C++ 代码中使用 printf 吗?
If I just want to print a string
on screen, I can do that using those two ways:
如果我只想string
在屏幕上打印一个,我可以使用这两种方式来做到这一点:
printf("abc");
std::cout << "abc" << std::endl;
The case is, and in the examples shown above, is there an advantage of using printf
over std::cout
, or, vice versa?
情况是,在上面显示的示例中,使用printf
over是否有优势std::cout
,反之亦然?
回答by dandan78
While cout
is the proper C++ way, I believe that some people and companies (including Google) continue to use printf
in C++ code because it is much easier to do formatted output with printf
than with cout
.
虽然cout
是正确的 C++ 方式,但我相信一些人和公司(包括Google)继续使用printf
C++ 代码,因为printf
使用cout
.
Here's an interesting example that I found here.
这是我在这里找到的一个有趣的例子。
Compare:
相比:
printf( "%-20s %-20s %5s\n" , "Name" , "Surname" , "Id" );
and
和
cout << setw( -20 ) << "Name" << setw( 20 ) << "Surname" << setw( 5 ) << "Id" << endl;
回答by Zac Howland
printf
and its associated friends are C functions. They work in C++, but do not have the type safety of C++ std::ostream
s. Problems can arise in programs that use printf
functions to format output based on user input (or even input from a file). For example:
printf
和它相关的朋友是 C 函数。它们在 C++ 中工作,但没有 C++ std::ostream
s的类型安全。在使用printf
函数根据用户输入(甚至来自文件的输入)格式化输出的程序中可能会出现问题。例如:
int main()
{
char[] a = {'1', '2', '3', '4'}; // a string that isn't 0-terminated
int i = 50;
printf("%s", a); // will continue printing characters until a 0 is found in memory
printf("%s", i); // will attempt to print a string, but this is actually an integer
}
C++ has much stronger type safety (and a std::string
class) to help prevent problems like these.
C++ 有更强大的类型安全(和一个std::string
类)来帮助防止这些问题。
回答by CashCow
Actually for your particular example, you should have asked which is preferable, puts or cout. printf prints formatted text but you are just outputting plain text to the console.
实际上,对于您的特定示例,您应该询问哪个更可取,puts 或 cout。printf 打印格式化文本,但您只是将纯文本输出到控制台。
For general use, streams (iostream, of which cout is a part) are more extensible (you can print your own types with them), and are more generic in that you can generate functions to print to any type of stream, not just the console (or redirected output). You can create generic stream behaviour with printf too using fprintf which take a FILE* as a FILE* is often not a real file, but this is more tricky.
对于一般用途,流(iostream,其中 cout 是其中的一部分)更具可扩展性(您可以用它们打印您自己的类型),并且更通用,因为您可以生成打印到任何类型流的函数,而不仅仅是控制台(或重定向输出)。您也可以使用 fprintf 使用 printf 创建通用流行为,它将 FILE* 作为 FILE* 通常不是真正的文件,但这更棘手。
Streams are "typesafe" in that you overload with the type you are printing. printf is not typesafe with its use of ellipses so you could get undefined results if you put the wrong parameter types in that do not match the format string, but the compiler will not complain. You may even get a seg-fault / undefined behaviour (but you could with cout if used incorrectly) if you miss a parameter or pass in a bad one (eg a number for %s and it treats it as a pointer anyway).
流是“类型安全的”,因为您可以使用正在打印的类型进行重载。printf 使用省略号不是类型安全的,因此如果您将错误的参数类型放入与格式字符串不匹配的内容中,您可能会得到未定义的结果,但编译器不会抱怨。如果您错过了一个参数或传入了一个错误的参数(例如 %s 的数字,无论如何它都将其视为指针),您甚至可能会遇到段错误/未定义的行为(但如果使用不当,您可能会使用 cout)。
printf does have some advantages though: you can template a format string then reuse that format string for different data, even if that data is not in a struct, and using formatting manipulations for one variable does not "stick" that format for further use because you specify the format for each variable. printf is also known to be threadsafe whereas cout actually is not.
printf 确实有一些优点:您可以模板化格式字符串,然后为不同的数据重用该格式字符串,即使该数据不在结构中,并且对一个变量使用格式操作不会“坚持”该格式以供进一步使用,因为您指定每个变量的格式。printf 也被认为是线程安全的,而 cout 实际上不是。
boost has combined the advantages of each with their boost::format library.
boost 结合了各自的优点和它们的 boost::format 库。
回答by vy32
I struggle with this very question myself. printf is in general easier to use for formatted printing, but the iostreams facility in C++ has the big advantage that you can create custom formatters for objects. I end up using both of them in my code as necessary.
我自己也在为这个问题而挣扎。printf 通常更容易用于格式化打印,但是 C++ 中的 iostreams 工具具有很大的优势,您可以为对象创建自定义格式化程序。我最终根据需要在我的代码中使用了它们。
The problem with using both and intermixing them is that the output buffers used by printf and cout are not the same, so unless you run unbuffered or explicitly flush output you can end up with corrupted output.
使用两者并混合使用它们的问题在于 printf 和 cout 使用的输出缓冲区不同,因此除非您运行无缓冲或显式刷新输出,否则最终可能会损坏输出。
My main objection to C++ is that there is no fast output formatting facility similar to printf, so there is no way to easily control output for integer, hex, and floating point formatting.
我对 C++ 的主要反对意见是没有类似于 printf 的快速输出格式化工具,因此无法轻松控制整数、十六进制和浮点格式的输出。
Java had this same problem; the language ended up getting printf.
Java 也有同样的问题;该语言最终得到了 printf。
Wikipedia has a good discussion of this issue at http://en.wikipedia.org/wiki/Printf#C.2B.2B_alternatives_to_sprintf_for_numeric_conversion.
维基百科在http://en.wikipedia.org/wiki/Printf#C.2B.2B_alternatives_to_sprintf_for_numeric_conversion上对此问题进行了很好的讨论。
回答by David Rodríguez - dribeas
The printf
has been borrowed from C and has some limitations. The most common mentioned limitation of printf
is type safety, as it relies on the programmer to correctly match the format string with the arguments. The second limitation that comes again from the varargs environment is that you cannot extend the behavior with user defined types. The printf
knows how to print a set of types, and that's all that you will get out of it. Still, it for the few things that it can be used for, it is faster and simpler to format strings with printf
than with c++ streams.
在printf
已经从C中借鉴并具有一定的局限性。最常见的限制printf
是类型安全,因为它依赖于程序员将格式字符串与参数正确匹配。来自 varargs 环境的第二个限制是您不能使用用户定义的类型扩展行为。Theprintf
知道如何打印一组类型,这就是您将从中获得的全部内容。尽管如此,对于它可以用于的少数事情,使用printf
C++ 流格式化字符串更快更简单。
While most modern compilers, are able to address the type safety limitation and at least provide warnings (the compiler can parse the format string and check the arguments provided in the call), the second limitation cannot be overcome. Even in the first case, there are things that the compiler cannot really help with, as checking for null termination --but then again, the same problem goes with std::cout
if you use it to print the same array.
虽然大多数现代编译器能够解决类型安全限制并至少提供警告(编译器可以解析格式字符串并检查调用中提供的参数),但无法克服第二个限制。即使在第一种情况下,编译器也无法真正提供帮助,例如检查空终止——但同样,std::cout
如果您使用它来打印相同的数组,也会出现同样的问题。
On the other end, streams (including std::cout
) can be extended to handle user defined types by means of overloaded std::ostream& operator<<( std::ostream&, type const & )
for any given user defined type type
. They are type safe by themselves --if you pass in a type that has no overloaded operator<<
the compiler will complain. They are, on the other hand, more cumbersome to produce formatted output.
另一方面,流(包括std::cout
)可以扩展为通过重载std::ostream& operator<<( std::ostream&, type const & )
任何给定的用户定义类型来处理用户定义的类型type
。它们本身是类型安全的——如果你传入一个没有重载operator<<
的类型,编译器会抱怨。另一方面,它们在生成格式化输出时更加麻烦。
So what should you use? In general I prefer using streams, as overloading operator<<
for my own types is simple and they can be used uniformly with all types.
那么你应该使用什么?一般来说,我更喜欢使用流,因为operator<<
我自己的类型的重载很简单,而且它们可以与所有类型统一使用。
回答by moinudin
Those two examples do different things. The latter will add a newline character and flush output (result of std::endl
). std::cout
is also slower. Other than that, printf
and std::cout
achieve the same thing and you can choose whichever you prefer. As a matter of preference, I'd use std::cout
in C++ code. It's more readable and safer.
这两个例子做不同的事情。后者将添加一个换行符并刷新输出(结果std::endl
)。std::cout
也比较慢。除此之外,printf
并std::cout
实现同样的事情,你可以选择你喜欢哪个。作为偏好,我会std::cout
在 C++ 代码中使用。它更具可读性和安全性。
See this articleif you need to format output using std::cout
.
请参阅这篇文章,如果您使用需要格式的输出std::cout
。
回答by Puppy
In general, you should prefer cout because it's much type-safer and more generic. printf isn't type-safe, nor is it generic at all. The only reason you might favour printf is speed- from memory, printf is many times faster than cout.
通常,您应该更喜欢 cout,因为它类型更安全且更通用。printf 不是类型安全的,也不是通用的。您可能喜欢 printf 的唯一原因是速度——从内存来看,printf 比 cout 快很多倍。