What is the difference between cout, cerr, clog of iostream header in c++? When to use which one?
Asked Answered
H

7

134

I tried researching the difference between cout, cerr and clog on the internet but couldn't find a perfect answer. I still am not clear on when to use which. Can anyone explain to me, through simple programs and illustrate a perfect situation on when to use which one?

I visited this site which shows a small program on cerr and clog, but the output obtained over there can also be obtained using cout. So, I'm confused over each one's exact use.

Hundredth answered 27/5, 2013 at 12:4 Comment(1)
Each one has a computer-recognized stream, stdout, stdin (for cin), and stderr that it uses by default. I believe clog is just cerr with a buffering change.Giro
A
72

stdout and stderr are different streams, even though they both refer to console output by default. Redirecting (piping) one of them (e.g. program.exe >out.txt) would not affect the other.

Generally, stdout should be used for actual program output, while all information and error messages should be printed to stderr, so that if the user redirects output to a file, information messages are still printed on the screen and not to the output file.

Antione answered 27/5, 2013 at 12:17 Comment(0)
E
158

Generally you use std::cout for normal output, std::cerr for errors, and std::clog for "logging" (which can mean whatever you want it to mean).

The major difference is that std::cerr is not buffered like the other two.


In relation to the old C stdout and stderr, std::cout corresponds to stdout, while std::cerr and std::clog both corresponds to stderr (except that std::clog is buffered).

Elvieelvin answered 27/5, 2013 at 12:5 Comment(5)
I've read that clog also outputs to cerr. So based on that, which one do you choose? If clog is normally for "logging", why would I want that to go to the error stream? Logs seem more like "normal logs" (a.k.a. cout) than errors.Bioplasm
@Bioplasm As I said in my answer, both cerr and clog uses the standard "error" output, but clog is buffered which might be why it seems more like cout. Which one to pick for error output? Depends I guess, on more reasons than I can list and it has to be decided from case to case.Elvieelvin
what do you mean by "buffered"?Polycarp
@Polycarp Output isn't written directly, it's stored in a buffer until the buffer is flushed. Output to a file or terminal is historically slow (terminals or consoles are still slow), writing character by character is ineffective, writing a chunk of bytes is much more effective.Elvieelvin
context: cerr is not buffered because if the program were to crash in a non-graceful way, you might have useful debugging info stuck in a buffer, rather than having been printed to stderr.Dyaus
A
72

stdout and stderr are different streams, even though they both refer to console output by default. Redirecting (piping) one of them (e.g. program.exe >out.txt) would not affect the other.

Generally, stdout should be used for actual program output, while all information and error messages should be printed to stderr, so that if the user redirects output to a file, information messages are still printed on the screen and not to the output file.

Antione answered 27/5, 2013 at 12:17 Comment(0)
S
28

Standard output stream (cout): cout is the instance of the ostream class. cout is used to produce output on the standard output device which is usually the display screen. The data needed to be displayed on the screen is inserted in the standard output stream (cout) using the insertion operator (<<).

Un-buffered standard error stream (cerr): cerr is the standard error stream which is used to output the errors. This is also an instance of the ostream class. As cerr is un-buffered so it is used when we need to display the error message immediately. It does not have any buffer to store the error message and display later.

Buffered standard error stream (clog): This is also an instance of ostream class and used to display errors but unlike cerr the error is first inserted into a buffer and is stored in the buffer until it is not fully filled.

further reading : basic-input-output-c

Spiritualty answered 12/9, 2017 at 6:45 Comment(3)
until it is not fully filled.--shouldn't this say until it IS fully filled?Fellah
FYI: It looks like TutorialsPoint.com has directly plagiarized your answer, here. I emailed TutorialsPoint on 23 Oct. 2020 about possible plagiarism, and they replied, "Sure Gabriel, we will look into it.", on 25 Oct. 2020. I never heard back from them after that, but it appears they did not look into it.Fellah
The plagiarism on TutorialsPoint.com is still there. What's the legal situation about this?Cyclades
M
12
  • Use cout for the standard output.
  • Use cerr to show errors.
  • Use clog for logging.
Marvismarwin answered 7/6, 2015 at 15:41 Comment(1)
Wrong, cerr is slower than cout because of non-buffer! Just like write vs printfDetest
R
12

The difference of these 3 streams is buffering.

  1. With cerr, the output flushs
    • immediately (because cerr does not use buffer).
  2. With clog, the output flushs
    • after you finish your current function.
    • explicitly call the function flush.
  3. With cout, the output flushs
    • after you have call to any output streams (cout, cerr, clog).
    • after you finish your current function.
    • explicitly call the function flush.

Please check the following code, and run DEBUG through 3 lines: f(std::clog), f(std::cerr), f(std::out), then open 3 output files to see what happened. You can swap these 3 lines to see what will happen.

#include <iostream>
#include <fstream>
#include <string>

void f(std::ostream &os)
{
    std::cin.clear(); // clear EOF flags
    std::cin.seekg(0, std::cin.beg); // seek to begin

    std::string line;
    while(std::getline(std::cin, line))   //input from the file in.txt
        os << line << "\n";   //output to the file out.txt
}

void test()
{
    std::ifstream in("in.txt");
    std::ofstream out("out.txt"), err("err.txt"), log("log.txt");
    std::streambuf *cinbuf = std::cin.rdbuf(), *coutbuf = std::cout.rdbuf(), *cerrbuf = std::cerr.rdbuf(),
                    *clogbuf = std::clog.rdbuf();

    std::cin.rdbuf(in.rdbuf()); //redirect std::cin to in.txt!
    std::cout.rdbuf(out.rdbuf()); //redirect std::cout to out.txt!
    std::cerr.rdbuf(err.rdbuf());
    std::clog.rdbuf(log.rdbuf());


    f(std::clog);
    f(std::cerr);
    f(std::cout);

    std::cin.rdbuf(cinbuf);
    std::cout.rdbuf(coutbuf);
    std::cerr.rdbuf(cerrbuf);
    std::clog.rdbuf(clogbuf);
}

int main()
{
    test();
    std::cout << "123";
}
Rooke answered 1/11, 2017 at 4:47 Comment(0)
O
6

From a draft C++17 standard document:

30.4.3 Narrow stream objects [narrow.stream.objects]

istream cin;

1 The object cin controls input from a stream buffer associated with the object stdin, declared in <cstdio> (30.11.1).

2 After the object cin is initialized, cin.tie() returns &cout. Its state is otherwise the same as required for basic_ios<char>::init (30.5.5.2).

ostream cout;

3 The object cout controls output to a stream buffer associated with the object stdout, declared in <cstdio> (30.11.1).

ostream cerr;

4 The object cerr controls output to a stream buffer associated with the object stderr, declared in<cstdio> (30.11.1).

5 After the object cerr is initialized, cerr.flags() & unitbuf is nonzero and cerr.tie() returns &cout. Its state is otherwise the same as required for basic_ios<char>::init (30.5.5.2).

ostream clog;

6 The object clog controls output to a stream buffer associated with the object stderr, declared in <cstdio> (30.11.1).

Discussion...

cout writes to stdout; cerr and clog to stderr

Standard Out (stdout) is intended to receive non-error, non-diagnostic output from the program, such as output from successful processing that can be displayed to the end-user or streamed into some further processing stage.

Standard Error (stderr) is intended for diagnostic output, such as warning and error messages that indicate the program hasn't or may not have produced the output the user might expect. This may be displayed to the end user even if the output data is piped to a further processing stage, or it could be redirected to a log file, for example.

cin and cerr are tied to cout

They both flush cout before handling I/O operations themselves. This ensures prompts sent to cout are visible before the program blocks to read input from cin, and that earlier output to cout is flushed before writing an error through cerr, which keeps the messages in chronological order of their generation when both are directed to the same terminal/file/etc..

This contrasts with clog - if you write there it won't be buffered and isn't tied to anything, so it will buffer decent sized amounts of logging before flushing. This yields the highest throughput of messages, but means the messages may not be quickly visible to a would-be consumer reading the terminal or tailing the log, even if an error was written through cerr and is on-screen or in the log.

Ostend answered 26/2, 2018 at 11:28 Comment(0)
D
1

Both cout and clog are buffered but cerr is un-buffered and all of these are predefined objects which are instances of class ostream. The basic use of these three are cout is used for standard output whereas clog and cerr is used for showing errors. The main point why cerr is un-buffered is may be because suppose you have several outputs in the buffer and an error exception is mentioned in the code then you need to display that error immediately which can be done by cerr effectively.

Please correct me if I am wrong.

Disentomb answered 10/8, 2017 at 14:30 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.