Re: A std::ostringstream wrapper for on-the-fly streaming - is this
dodgy?
On Aug 5, 11:28 am, James Kanze <james.ka...@gmail.com> wrote:
On Aug 5, 12:54 am, Francesco <entul...@gmail.com> wrote:
On Aug 5, 12:46 am, Francesco <entul...@gmail.com> wrote:
[snip]
I've been able to compile the "operator<<(T& (*manip)(T&))"
function but it wasn't able to accept any manipulator at
all.
[snip]
Correction: it accepts many manipulators, but not all of them
(in particular, it doesn't accept std::endl)
I don't think so, if it's a template. The manipulators which
don't take an argument are function templates; you need template
argument type deduction to work in order to use them, and
passing them (or their address, which is what is actually
happening) as an argument to another function template, which
needs their type for its argument deduction, doesn't work (and
can't be made to work---there's a fundamental cyclic dependency
here). The manipulators which take an argument return an object
with a specific type, which is handled by the "template <
typename T > operator<<( T const& )"; they don't normally return
a pointer to a function. (In theory, they could, but in
practice, they need at least one additional data---the
manipulator argument.)
Once again, James, believe me I have no idea of what is going on. I'm
just the trial-and-error type of guy, waiting for the moment that this
stuff becomes more clear to me.
Here is the template-only version of the logger, which accepts almost
all manipulators:
-------
#include <iostream>
#include <iomanip>
struct o_template {
std::ostream* stream;
o_template() : stream(0) {};
template<class T> o_template& operator<<(T& (*f)(T&)) {
if (stream) (*stream) << f;
return *this;
}
};
int main()
{
o_template ot_cout;
ot_cout.stream = &std::cout;
/* accepted manipulators */
ot_cout << std::boolalpha;
ot_cout << std::dec;
ot_cout << std::fixed;
ot_cout << std::hex;
ot_cout << std::internal;
ot_cout << std::left;
ot_cout << std::noboolalpha;
ot_cout << std::noshowbase;
ot_cout << std::noshowpoint;
ot_cout << std::noshowpos;
ot_cout << std::nounitbuf;
ot_cout << std::nouppercase;
ot_cout << std::oct;
ot_cout << std::right;
ot_cout << std::scientific;
ot_cout << std::showbase;
ot_cout << std::showpoint;
ot_cout << std::showpos;
ot_cout << std::unitbuf;
ot_cout << std::uppercase;
ot_cout << std::skipws;
ot_cout << std::noskipws;
/* not-accepted manipulators */
// ot_cout << std::endl;
// ot_cout << std::ends;
// ot_cout << std::flush;
// ot_cout << std::resetiosflags(std::ios_base::showbase);
// ot_cout << std::setbase(10);
// ot_cout << std::setfill(' ');
// ot_cout << std::setiosflags(std::ios_base::showbase);
// ot_cout << std::setprecision(10);
// ot_cout << std::setw(10);
// ot_cout << std::ws;
return 0;
}
-------
Up to you to understand what's going on, for me it's just enough to
know that it works.
Of course, I'm not using this template in my code, I use the "(const
T& t)" version along with the "istream / ostream" functions I
mentioned in my "io_logger" parents.
By the way, @Stuart, changing "std::ios" to "std::ios_base" makes no
difference at all, in my compiler - no manip accepted either.
And also, Stu, please, don't take all these posts of mine as an
attempt to HJ your thread ;-)
Have good time,
cheers,
Francesco.
--
James Kanze (GABI Software) email:james.ka...@gma=
il.com
Conseils en informatique orient=E9e objet/
Beratung in objektorientierter Dat=
enverarbeitung
9 place S=E9mard, 78210 St.-Cyr-l'=C9cole, France, +33 (0)1 30 23 00 34