here is my function
ostream margain(std::string firstWord)
{
ostream x;
x << std::setw(20) << firstWord;
return x;
}
in main I want to use the function as follow
std::cout<< margain("start") << "````````````````````````````````````" << std::endl;
// print things out
//then
std::cout<< margain("End") << "````````````````````````````````````" << std::endl;
I get the output, start or end is not shown, and the return value is
0````````````````````````````````````
how can I fix it? and why?
Edit: I know that the function is what causing that, because if I add this
cout << std::setw(20) << firstWord; in the function, It prints right,
I fixed it, not the best way, but as
calling the function as
margain(std::cout, "End") << "~=~=~=~=~=~=~=~=~=~=~=~=~=~=~=~=~=~=~=~=~=~=~=~=~" << endl;
the function looks like
ostream& margain(ostream& stream, std::string firstWord)
{
stream << std::left << std::setw(10) << firstWord;
return stream;
}
anyone know better way?
You are printing the value of the ostream, not value of firstword
. The ostream x
in this case is an unopened stream, so it doesn't "do" anything. Because the compiler allows to conversion to either bool
(C++11) or void *
(before C++11), the "value" from that conversion is printed. Note that any operations on x
will not affect cout
.
The easiest solution, I would think is to actually add std::setw(20)
to your output line:
std::cout<< std::setw(20 << "End" << "````````````````````````````````````" << std::endl;
The other choice would be to pass the std::cout
to margain
, and return the std::string
, something like this:
std::string margain(ostream& x, const std::string& firstWord)
{
x << std::setw(20);
return firstWord;
}
then you could do:
std::cout<< margain(cout, "start") << "````````````````````````````````````" << std::endl;
But it's not exactly flexible or "neat".
The third option is of course to have a MarginString
class:
class MarignString
{
private:
int margin;
std::string str;
public:
MarginString(int margin, std::string str) margin(margin), str(str) {}
operator std::string() { return str; }
friend std::ostream& operator(std::ostream& os, const MarginString& ms);
};
std::ostream& operator(std::ostream& os, const MarginString& ms)
{
os << std::setw(ms.margin) << ms.str;
return os;
}
...
std::cout<< MarginString(20, "start") << "````````````````````````````````````" << std::endl;
Note that this last way is probably not that great either... ;)