问题
I am trying to use set width setw
for string output to an output file, however, I am not able to make it work. I have with me the following example.
// setw example
#include <iostream>
#include <iomanip>
#include <fstream>
int main () {
std::ofstream output_file;
output_file.open("file.txt");
output_file << "first" <<std::setw(5)<< "second"<< std::endl;
output_file.close();
return 0;
}
Edit:
With the above lines I expected to have many spaces between first
and second
, something like
first second
I hardly see any spaces, the output just comes like firstsecond
I think I missed the working of setw()
Note: For integers, it works fine just:
output_file << 1 <<std::setw(5)<< 2 << std::endl;
What I am doing wrong??.
回答1:
I suspect your understanding of std::setw
is simply not correct. I think you need something more along the lines of a combination of:
- std::setw for setting field width
- std::setfill for setting the fill character
- std::left, std::right, std::internal for setting the write position within the specified field width.
What is happening in your code:
- Uses
std::setw(5)
to establish a field width of five characters. - Sends
"first"
to the stream, which is five characters long, so the established field width is completely consumed. No additional filling takes place. - Sends
"second"
to the stream, which is six characters long, so again, the entire field width is consumed (and in-fact breached). Again, no filling takes place
If you're intent is to have something like this (with column numbers above to show positions):
col: 0123456789012345678901234567890123456789
first second third fourth
Notice how each word starts on an even multiple of 10 boundary. One way to do that is by using :
- A output position
std::left
(so the fill, if any goes on the right to achieve the desired width). This the default for strings, but it never hurts to be sure. - A fill character of
std::setfill(' ')
. Again, the default. - A field width
std::setw(10)
Why such a large number? See below
Example
#include <iostream>
#include <iomanip>
int main ()
{
std::cout << std::left << std::setfill(' ')
<< std::setw(10) << "first"
<< std::setw(10) << "second"
<< std::setw(10) << "third"
<< std::setw(10) << "fourth" << '\n';
return 0;
}
Output (column numbers added)
0123456789012345678901234567890123456789
first second third fourth
So what happens if we change the output location to std::right
? Well, with the identical program, changing only the first line to :
std::cout << std::right << std::setfill(' ')
we get
0123456789012345678901234567890123456789
first second third fourth
Finally, one constructive way of seeing where the fill characters are being applied is by simply changing the fill char to something visible (ie. something besides a space). The last two examples output, changing the fill char to std::setfill('*')
produces the following output:
First
first*****second****third*****fourth****
Second
*****first****second*****third****fourth
Notice in both cases, since none of the individual output items breached the std::setw
value, the total output line size for each is the same. All that changed was where the fills were applied and the output aligned within the std::setw
specification.
来源:https://stackoverflow.com/questions/42242202/how-does-stdsetw-work-with-string-output