7
#include <iostream> using namespace std; int main() { cout << -0.152454345 << " " << -0.7545 << endl; cout << 0.15243 << " " << 0.9154878774 << endl; } 

Outputs:

-0.152454 -0.7545 0.15243 0.915488 

I want the output to look like this:

-0.152454 -0.754500 0.152430 0.915488 

My solution:

#include <iostream> #include <iomanip> using namespace std; int main() { cout << fixed << setprecision(6) << setw(9) << setfill(' ') << -0.152454345 << " "; cout << fixed << setprecision(6) << setw(9) << setfill(' ') << -0.7545 << endl; cout << fixed << setprecision(6) << setw(9) << setfill(' ') << 0.15243 << " "; cout << fixed << setprecision(6) << setw(9) << setfill(' ') << 0.9154878774 << endl; } 

The output is good, but the code is terrible. What can be done? Here is my code https://ideone.com/6MKd31

3
  • 2
    Use stdio.h. iostream is bad for formatting. Commented Mar 15, 2018 at 9:12
  • You could write a function for it? Commented Mar 15, 2018 at 9:59
  • 1
    A nice guide that explains the basics of numeric formatting and shows good code examples: websites.umich.edu/~eecs381/handouts/formatting.pdf Commented Mar 5, 2023 at 18:20

5 Answers 5

9

Specifying an output format is always terrible. Anyway you can just omit to repeat stream modifiers that are conserved across input/output and repeat only those that are transients (setw):

// change state of the stream cout << fixed << setprecision(6) << setfill(' '); // output data cout << setw(9) << -0.152454345 << " "; cout << setw(9) << -0.7545 << endl; cout << setw(9) << 0.15243 << " "; cout << setw(9) << 0.9154878774 << endl; 
Sign up to request clarification or add additional context in comments.

Comments

3

This might not quite be what you want, but I thought I'd throw it out there anyway as it's very simple.

If you can tolerate a leading + for non-negative numbers then you can use

std::cout << std::showpos << /*ToDo - the rest of your output here*/ 

At least then everything lines up, with minimal effort.

Comments

3

Had a similar problem with streams once (but more complex, though), you could use a separate formatter object to avoid code repeating:

class F { double v; public: F(double v) : v(v) { }; friend ostream& operator<<(ostream& s, F f) { s << setw(9) << v; } }; 

Usage:

std::cout << fixed << setprecision(6) << setfill(' '); // retained, see Jean's answer std::cout << F(12.10) << ' ' << F(-10.12) << std::endl; 

Depending on your needs and how frequently you use it, it might be overkill or not - decide yourself...

Comments

3

You can write a function for it:

std::ostream& format_out(std::ostream& os, int precision, int width, char fill, double value) { return os << std::fixed << std::setprecision(precision) << std::setw(width) << std::setfill(fill) << value; } int main() { format_out(std::cout, 6, 9, ' ', -0.152454345) << '\n'; format_out(std::cout, 6, 9, ' ', -0.7545) << '\n'; format_out(std::cout, 6, 9, ' ', 0.15243) << '\n'; format_out(std::cout, 6, 9, ' ', 0.9154878774) << '\n'; } 

Comments

2

A bit of necroposting, but it might still be useful to someone in the future. We can use a lamda expression (or the equivalent function) to make the formatting less painful.

#include <iostream> #include <iomanip> int main() { using namespace std; auto format = [](std::ostream &os) -> std::ostream& { return os << fixed << setprecision(6) << setw(9) << setfill(' '); }; cout << format << -0.152454345 << " " << format << -0.7545 << "\n"; cout << format << 0.15243 << " " << format << 0.9154878774 << endl; } 

Output:

-0.152454 -0.754500 0.152430 0.915488 

1 Comment

Clever, and I like to learn about lambda, so +1, but I won't use this for formatting right now

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.