Go to main content
Oracle® Developer Studio 12.5: C++ User's Guide

Exit Print View

Updated: July 2016
 
 

13.7 Manipulators

Manipulators are values that you can insert into or extract from iostreams to have special effects.

Parameterized manipulators are manipulators that take one or more parameters.

Because manipulators are ordinary identifiers and therefore use up possible names, iostream does not define them for every possible function. A number of manipulators are discussed with member functions in other parts of this chapter.

The 13 predefined manipulators are described in the following table. This table assumes the following:

  • i has type long.

  • n has type int.

  • c has type char.

  • istr is an input stream.

  • ostr is an output stream.

Table 27  iostream Predefined Manipulators
Predefined Manipulator
Description
1
ostr << dec, istr >> dec
Makes the integer conversion base 10.
2
ostr << endl
Inserts a newline character (’\n’) and invokes ostream::flush().
3
ostr << ends
Inserts a null (0) character. Useful when dealing with strstream.
4
ostr << flush
Invokes ostream::flush().
5
ostr << hex, istr >> hex
Makes the integer conversion base 16.
6
ostr << oct, istr >> oct
Make the integer conversion base 8.
7
istr >> ws
Extracts whitespace characters (skips whitespace) until a non-whitespace character is found (which is left in istr).
8
ostr << setbase(n), istr >> setbase(n)
Sets the conversion base to n (0, 8, 10, 16 only).
9
ostr << setw(n), istr >> setw(n)
Invokes ios::width(n). Sets the field width to n.
10
ostr << resetiosflags(i), istr>> resetiosflags(i)
Clears the flags bitvector according to the bits set in i.
11
ostr << setiosflags(i), istr >> setiosflags(i)
Sets the flags bitvector according to the bits set in i.
12
ostr << setfill(c), istr >> setfill(c)
Sets the fill character (for padding a field) to c.
13
ostr << setprecision(n), istr >> setprecision(n)
Sets the floating-point precision to n digits.

To use predefined manipulators, you must include the file iomanip.h in your program.

You can define your own manipulators. The two basic types of manipulators are:

  • Plain manipulator – Takes an istream&, ostream&, or ios& argument, operates on the stream, and then returns its argument.

  • Parameterized manipulator – Takes an istream&, ostream&, or ios& argument, one additional argument (the parameter), operates on the stream, and then returns its stream argument.

13.7.1 Using Plain Manipulators

A plain manipulator is a function that performs the following actions:

  • Takes a reference to a stream

  • Operates on the stream in some way

  • Returns its argument

The shift operators taking a pointer to such a function are predefined for iostreams so the function can be put in a sequence of input or output operators. The shift operator calls the function rather than trying to read or write a value. The following example shows a tab manipulator that inserts a tab in an ostream is:

ostream& tab(ostream& os) {
             return os <<’\t’;
            }
...
cout << x << tab << y;

This example is an elaborate way to achieve the following code:

const char tab = ’\t’;
...
cout << x << tab << y;

The following code is another example, which cannot be accomplished with a simple constant. Suppose you want to turn whitespace skipping on and off for an input stream. You can use separate calls to ios::setf and ios::unsetf to turn the skipws flag on and off, or you could define two manipulators.

#include <iostream.h>
#include <iomanip.h>
istream& skipon(istream &is) {
       is.setf(ios::skipws, ios::skipws);
       return is;
}
istream& skipoff(istream& is) {
       is.unsetf(ios::skipws);
       return is;
}
...
int main ()
{
      int x,y;
      cin >> skipon >> x >> skipoff >> y;
      return 1;
}

13.7.2 Parameterized Manipulators

One of the parameterized manipulators that is included in iomanip.h is setfill. setfill sets the character that is used to fill out field widths. This manipulator is implemented as shown in the following example:

//file setfill.cc
#include<iostream.h>
#include<iomanip.h>

//the private manipulator
static ios& sfill(ios& i, int f) {
         i.fill(f);
         return i;
}
//the public applicator
smanip_int setfill(int f) {
       return smanip_int(sfill, f);
}

A parameterized manipulator is implemented in two parts:

  • The manipulator. It takes an extra parameter. In the previous code example, it takes an extra int parameter. You cannot place this manipulator function in a sequence of input or output operations, because no shift operator is defined for it. Instead, you must use an auxiliary function, the applicator.

  • The applicator. It calls the manipulator. The applicator is a global function, and you make a prototype for it available in a header file. Usually the manipulator is a static function in the file containing the source code for the applicator. The manipulator is called only by the applicator. If you make it static, you keep its name out of the global address space.

Several classes are defined in the header file iomanip.h. Each class holds the address of a manipulator function and the value of one parameter. The iomanip classes are described in the manip(3CC4) man page. The previous example uses the smanip_int class, which works with an ios. Because it works with an ios, it also works with an istream and an ostream. The previous example also uses a second parameter of type int.

The applicator creates and returns a class object. In the previous code example the class object is an smanip_int, and it contains the manipulator and the int argument to the applicator. The iomanip.h header file defines the shift operators for this class. When the applicator function setfill appears in a sequence of input or output operations, the applicator function is called, and it returns a class. The shift operator acts on the class to call the manipulator function with its parameter value, which is stored in the class.

In the following example, the manipulator print_hex performs the following actions:

  • Puts the output stream into the hex mode

  • Inserts a long value into the stream

  • Restores the conversion mode of the stream

The class omanip_long is used because this code example is for output only. It operates on a long rather than an int:

#include <iostream.h>
#include <iomanip.h>
static ostream& xfield(ostream& os, long v) {
        long save = os.setf(ios::hex, ios::basefield);
        os << v;
        os.setf(save, ios::basefield);
        return os;
    }
omanip_long print_hex(long v) {
       return omanip_long(xfield, v);
   }