C++ Syntax: Input/Output: << >>
Description
Standard Streams
The standard I/O system is declared in the
header file:-
#include <iosteam.h>
I/O sources and sinks are called streams. 3 are defined in the header:-
- cin The standard input, normally the keyboard.
- cout The standard output, normally the screen.
- cerr The error output, normally the screen.
I/O can be achieved just by using the appropriate function defined in the
header. To print out the value of some basic type called x followed by a
newline ("\n"):-
put(cout,"x = ");
put(cout,x);
put(cout,"\n");
Two functions are being used here, but they are both called put,
(i.e. the function is overloaded).
It is the compiler's job to work out which to use based on the context, i.e.
the type of arguments.
Overloading << and >>
The above is verbose so a more elegant way is provided.
The C++ language does not
include an I/O system, but one of its core concepts is
that it is extendible. Although its operator set cannot be increased, the
meanings of operators depend on the context in which they are used. When
applied to new objects the meaning can be redefined. So, the left shift
operator << has, in the standard I/O library, been overloaded to be the
put function when its left hand argument is an input stream. Hence:-
cout << "x = ";
is the same as
put(cout,"x = ");
The side effect is to output the right hand variable and the expression
produces a value that is an output stream (technically its a
reference
to an output stream, but it amounts to the same thing). This value
can be used again as the left hand size of a <<. So to call the
put functions 3 times as before:-
cout << "x = " << x << "\n";
because the << operator is evaluated left to right.
It take a little getting
used to for a FORTRAN programmer, but after a while you get used to seeing
this as a cout object with a stream of values flowing into it.
As you might expect, input simply reverses the sign on the flow, so to read 3
numbers from the input stream and store them in x, y, z:-
cin >> x >> y >> z;
Modifiers
At first sight this all looks very inflexible. What if you want to
format the output to print floating
point numbers to 3 decimal places? The solution is to introduce special data
types into the values being input or output and then to define new functions
that overload the shift operators to be called when it comes across such data
types. Consider:-
cout << hex << my_int << endl;
hex and endl are manipulators, that result in special functions being called
when they are processed:-
- hex changes the state of the stream so that following integers,
my_int in this case, are printed in hexadecimal. As you might expect, there
are also dec and oct manipulators.
- endl adds a newline ("\n") and also flushes the buffer. So its
better than just "\n" if you want to see the output at once.
There are more complicated manipulators that take arguments, for example:-
cout << setprecision(4) << my_float;
This sets floating point precision to 4 digits, ready to output my_float.
Manipulators that take arguments are a bit more complicated. Basically, the
function setprecision creates an object that knows what the user wants.
Then the compiler finds an definition of the << operator that can be used
with this object, and this definition calls the object to do the user's
bidding. You don't need to know any of this, but it is a nice example of how
flexible objects are, in this case being created just to pass a message from
the user to the output stream. To use manipulators that take arguments you
have to include:-
#include <iomanip.h>
A couple of other manipulators of this type are:-
- setfill(int c) - set the fill character to c.
- setw(int w) - set the field width to w.
Extending the I/O System
Although the standard streams know only how to perform I/O on the standard
data types, the user can extend the operators to apply to his or her own
classes.
It is also possible to define new streams. ROOT does this in its I/O,
defining the << and the >> to stream data to/from its own buffer
classes.
See operator
precedence
Other Uses for << >>
<< >> are the
shift
operators. As explained above this is an example
of operator reuse.
Usage Notes
None.
Go Back to the
The C++ Crib Top Page
If you have any comments about this page please send them to
Nick West