Briefly dismiss the fact that normal function overloading will serve this example better. It is meant only as a way to learn about template programming. Having said that, you are welcome to comment on the benefits/differences you'll get from using function overload, compared to function template specialization (although that might deserve a question of its own).
Consider the following example:
template <typename T>
inline void ToString(T value, char* target, size_t max_size );
template <>
inline void ToString<float>(float value, char* target, size_t max_size)
{
snprintf( target , max_size , "%f" , value);
}
template <>
inline void ToString<double>(double value, char* target, size_t max_size)
{
snprintf( target , max_size , "%f" , value);
}
Is there a way to write only one of these specializations that match both float
and double
types?
Basically I envision writing a template specialization for a template type that will match both float
and double
(as sort of 'float or double' type matcher) but I'm not sure whether that is possible at all with C++. That said, I've seen unexpected template magic happen in front of my eyes before, so I think it's a good question to ask here.
Here's a standard solution idiom:
#include <type_traits>
#include <cstdio>
// Helper class
template <typename T>
struct Printer
{
static typename std::enable_if<std::is_floating_point<T>::value, int>::type
print(T x, char * out, std::size_t n)
{
return std::snprintf(out, n, "%f", x);
}
};
// Convenience function wrapper
template <typename T> int print(T x, char * out, std::size_t n)
{
return Printer<T>::print(x, out, n);
}
void f()
{
char a[10];
Printer<double>::print(1.2, a, 10); // use helper class
print(1.4f, a, 10); // wrapper deduces type for you
}
You'll get a compile-time error if you call either construction with a non-floating type. Beware though that this might erroneously work for long doubles, which require the %Lf
format specifier; and also recall that floats get promoted to doubles when passed through variadic function arguments.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With