It is late in the night. My brain is not functioning. I couldn't
figure out how to do a simple thing. I want to write a template
function that take a single input parameter and print the value of
that parameter into a stream. Here is what I have:
template<typename T>
void Print( std::ostream& output, const T& a )
{
output << a;
}
Now the function works for all T whereas operator<<( std::ostream&,
const T& ) is defined. For those Ts that operator<< is not defined, I
would like function "Print" to print a sentence "do not know how to
print the value".
Anybody know how to modify the template function to print the value if
it can, and print "do not know how to print the value" otherwise?
[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]
> It is late in the night. My brain is not functioning. I couldn't
> figure out how to do a simple thing. I want to write a template
> function that take a single input parameter and print the value of
> that parameter into a stream. Here is what I have:
>
> template<typename T>
> void Print( std::ostream& output, const T& a )
> {
> output << a;
> }
>
> Now the function works for all T whereas operator<<( std::ostream&,
> const T& ) is defined. For those Ts that operator<< is not defined, I
> would like function "Print" to print a sentence "do not know how to
> print the value".
>
> Anybody know how to modify the template function to print the value if
> it can, and print "do not know how to print the value" otherwise?
Look at is_incrementable.hpp from boost for inspiration:
#include <iostream>
// resembles one from boost
template<bool> struct bool_ {};
typedef bool_<false> false_;
typedef bool_<true> true_;
namespace is_left_shiftable_ {
struct tag {};
struct any { template<class T> any(T const&); };
tag operator<<(any const&, any const&);
template<class T, class U>
struct is_left_shiftable_impl
{
typedef char(&no)[1];
typedef char(&yes)[2];
static no check(tag);
static yes check(...);
static T* t;
static U* u;
enum { value = (sizeof(yes) == sizeof(check(*t << *u))) };
typedef bool_<value> type;
};
} // namespace is_left_shiftable_
template<class T, class U>
struct is_left_shiftable : is_left_shiftable_::is_left_shiftable_impl<T, U>
{
};
template<class T>
std::ostream& print_impl(std::ostream& s, T const&, false_)
{
return s << "do not know how to print the value";
}
template<class T>
std::ostream& print_impl(std::ostream& s, T const& t, true_)
{
return s << t;
}
template<class T>
std::ostream& print(std::ostream& s, T const& t)
{
typedef typename is_left_shiftable<std::ostream, T>::type flag;
return print_impl(s, t, flag());
}
struct non_printable {};
int main()
{
print(std::cout, 1) << '\n';
print(std::cout, non_printable()) << '\n';
}
--
Maxim Yegorushkin
Don't be so hard on yourself; this is actually not that simple.
> I want to write a template
> function that take a single input parameter and print the value of
> that parameter into a stream. Here is what I have:
>
> template<typename T>
> void Print( std::ostream& output, const T& a )
> {
> output << a;
> }
>
> Now the function works for all T whereas operator<<( std::ostream&,
> const T& ) is defined. For those Ts that operator<< is not defined, I
> would like function "Print" to print a sentence "do not know how to
> print the value".
>
> Anybody know how to modify the template function to print the value if
> it can, and print "do not know how to print the value" otherwise?
Terje Slettebř showed how to test for the presence of an operator in
<http://groups.google.com/groups?selm=q2vBa.9199%24KF1.136318%40amstwist00>.
> It is late in the night. My brain is not functioning. I couldn't
> figure out how to do a simple thing. I want to write a template
> function that take a single input parameter and print the value of
> that parameter into a stream. Here is what I have:
>
> template<typename T>
> void Print( std::ostream& output, const T& a )
> {
> output << a;
> }
>
> Now the function works for all T whereas operator<<( std::ostream&,
> const T& ) is defined. For those Ts that operator<< is not defined, I
> would like function "Print" to print a sentence "do not know how to
> print the value".
>
> Anybody know how to modify the template function to print the value if
> it can, and print "do not know how to print the value" otherwise?
Look at is_incrementable.hpp from boost for inspiration:
#include <iostream>
namespace is_left_shiftable_ {
} // namespace is_left_shiftable_
struct non_printable {};
--
Maxim Yegorushkin
[ See http://www.gotw.ca/resources/clcm.htm for info about ]