Manipulators are helping functions that can modify the input/output (Links to an external site.) stream. It does not mean that we change the value of a variable, it only modifies the I/O stream using insertion (<<) and extraction (>>) operators.
For example, if we want to print the hexadecimal value of 100 then we can print it as:
cout<<setbase(16)<<100
Types of Manipulators
There are various types of manipulators:
-
Manipulators without arguments: The most important manipulators defined by the IOStream library are provided below.
- endl: It is defined in ostream. It is used to enter a new line and after entering a new line it flushes (i.e. it forces all the output written on the screen or in the file) the output stream.
- ws: It is defined in istream and is used to ignore the whitespaces in the string sequence.
- ends: It is also defined in ostream and it inserts a null character into the output stream. It typically works with std::ostrstream, when the associated output buffer needs to be null-terminated to be processed as a C string.
-
flush: It is also defined in ostream and it flushes the output stream, i.e. it forces all the output written on the screen or in the file. Without flush, the output would be the same, but may not appear in real-time.
Examples:
#include <iostream>
#include <istream>
#include <sstream>
#include <string>
using
namespace
std;
int
main()
{
istringstream str(
" Programmer"
);
string line;
// Ignore all the whitespace in string
// str before the first word.
getline(str >> std::ws, line);
// you can also write str>>ws
// After printing the output it will automatically
// write a new line in the output stream.
cout << line << endl;
// without flush, the output will be the same.
cout <<
"only a test"
<< flush;
// Use of ends Manipulator
cout <<
"\na"
;
// NULL character will be added in the Output
cout <<
"b"
<< ends;
cout <<
"c"
<< endl;
return
0;
}
Output:Programmer only a test abc
-
Manipulators with Arguments: Some of the manipulators are used with the argument like setw (20), setfill (‘*’), and many more. These all are defined in the header file. If we want to use these manipulators then we must include this header file in our program.
For Example, you can use following manipulators to set minimum width and fill the empty space with any character you want: std::cout << std::setw (6) << std::setfill (’*’);
-
Some important manipulators in <iomanip> are:
- setw (val): It is used to set the field width in output operations.
- setfill (c): It is used to fill the character ‘c’ on output stream.
- setprecision (val): It sets val as the new value for the precision of floating-point values.
- setbase(val): It is used to set the numeric base value for numeric values.
- setiosflags(flag): It is used to set the format flags specified by parameter mask.
- resetiosflags(m): It is used to reset the format flags specified by parameter mask.
-
Some important manipulators in <ios> are:
- showpos: It forces to show a positive sign on positive numbers.
- noshowpos: It forces not to write a positive sign on positive numbers.
- showbase: It indicates the numeric base of numeric values.
- uppercase: It forces uppercase letters for numeric values.
- nouppercase: It forces lowercase letters for numeric values.
- fixed: It uses decimal notation for floating-point values.
- scientific: It uses scientific floating-point notation.
- hex: Read and write hexadecimal values for integers and it works same as the setbase(16).
- dec: Read and write decimal values for integers i.e. setbase(10).
- oct: Read and write octal values for integers i.e. setbase(10).
- left: It adjusts output to the left.
- right: It adjusts output to the right.
Example:
#include <iomanip>
#include <iostream>
using
namespace
std;
int
main()
{
double
A = 100;
double
B = 2001.5251;
double
C = 201455.2646;
// We can use setbase(16) here instead of hex
// formatting
cout << hex << left << showbase << nouppercase;
// actual printed part
cout << (
long
long
)A << endl;
// We can use dec here instead of setbase(10)
// formatting
cout << setbase(10) << right << setw(15)
<< setfill(
'_'
) << showpos
<< fixed << setprecision(2);
// actual printed part
cout << B << endl;
// formatting
cout << scientific << uppercase
<< noshowpos << setprecision(9);
// actual printed part
cout << C << endl;
}
Output:0x64 _______+2001.53 2.014552646E+05
static_cast in C++ | Type Casting operators
A Cast operator is an unary operator which forces one data type to be converted into another data type.
C++ supports four types of casting:1. Static Cast
2. Dynamic Cast
3. Const Cast (Links to an external site.)
4. Reinterpret Cast (Links to an external site.)Static Cast: This is the simplest type of cast which can be used. It is a compile time cast.It does things like implicit conversions between types (such as int to float, or pointer to void*), and it can also call explicit conversion functions (or implicit ones).
For e.g.#include <iostream>
using
namespace
std;
int
main()
{
float
f = 3.5;
int
a = f;
// this is how you do in C
int
b =
static_cast
<
int
>(f);
cout << b;
}
Output:
3
Now let’s make a few changes in the code.
#include <iostream>
using
namespace
std;
int
main()
{
int
a = 10;
char
c =
'a'
;
// pass at compile time, may fail at run time
int
* q = (
int
*)&c;
int
* p =
static_cast
<
int
*>(&c);
return
0;
}
If you compile the code, you will get an error:
[Error] invalid static_cast from type 'char*' to type 'int*'
This means that even if you think you can some how typecast a particular object int another but its illegal, static_cast will not allow you to do this.
Lets take another example of converting object to and from a class.
#include <iostream>
#include <string>
using
namespace
std;
class
Int {
int
x;
public
:
Int(
int
x_in = 0)
: x{ x_in }
{
cout <<
"Conversion Ctor called"
<< endl;
}
operator string()
{
cout <<
"Conversion Operator"
<< endl;
return
to_string(x);
}
};
int
main()
{
Int obj(3);
string str = obj;
obj = 20;
string str2 =
static_cast
<string>(obj);
obj =
static_cast
<Int>(30);
return
0;
}
Run the above code:
Conversion Ctor called Conversion Operator Conversion Ctor called Conversion Operator Conversion Ctor called
Lets the try to understand the above output:
- When obj is created then constructor is called which in our case is also a Conversion Constructor(For C++14 rules are bit changed).
- When you create str out of obj, compiler will not thrown an error as we have defined the Conversion operator.
- When you make
obj=20
, you are actually calling the conversion constructor. - When you make str2 out of static_cast, it is quite similar to
string str=obj;
, but with a tight type checking. - When you write
obj=static_cast<Int>(30)
, you are converting 30 into Int using static_cast.
Lets take example which involves Inheritance.
#include <iostream>
using
namespace
std;
class
Base {
};
class
Derived :
public
Base {
};
int
main()
{
Derived d1;
Base* b1 = (Base*)(&d1);
// allowed
Base* b2 =
static_cast
<Base*>(&d1);
return
0;
}
The above code will compile without any error.
- We took address of
d1
and explicitly casted it intoBase
and stored it inb1
. - We took address of
d1
and used static_cast to cast it intoBase
and stored it inb2
.
As we know static_cast performs a tight type checking, let’s the changed code slightly to see it:
#include <iostream>
using
namespace
std;
class
Base {
};
class
Derived :
private
Base {
// Inherited private/protected not public
};
int
main()
{
Derived d1;
Base* b1 = (Base*)(&d1);
// allowed
Base* b2 =
static_cast
<Base*>(&d1);
return
0;
}
Try to compile the above code, What do you see?? Compilation Error!!!!!!!
[Error] 'Base' is an inaccessible base of 'Derived'
The above code will not compile even if you inherit as protected. So to use static_cast, inherit it as public.
Use static_cast to cast ‘to and from’ void pointer.
#include <iostream>
int
main()
{
int
i = 10;
void
* v =
static_cast
<
void
*>(&i);
int
* ip =
static_cast
<
int
*>(v);
return
0;
}
-
Some important manipulators in <iomanip> are: