Reputation: 6340
Does template specialization work with alias templates? Specifically, the following code throws an unexpected error:
$ cat test01.h
#ifndef TEST01_H
#define TEST01_H
#include <iostream>
#include <typeinfo>
#include <cstdlib>
template <template <typename> class Ops>
double add1(double const & x) {
std::cerr << "Undefined for type: " << typeid(Ops <double>).name() << std::endl;
exit(EXIT_FAILURE);
}
template <typename Real>
struct MyOps {
static Real add(Real const & x,Real const & y) {
return x+y;
}
};
template <typename Real> using MyOpsAlias = MyOps <Real>;
#endif
In addition,
$ cat test01.cpp
#include "test01.h"
template <>
double add1 <MyOps> (double const & x) {
return MyOps <double>::add(x,1.);
}
int main() {
std::cout << add1 <MyOps> (2.) << std::endl;
std::cout << add1 <MyOpsAlias> (2.) << std::endl;
}
After running this code, I receive
$ ./test01
3
Undefined for type: 5MyOpsIdE
I expected that both answers should return 3 since MyOpsAlias should just be an alias template of MyOps. In case it matters, I'm using GCC 4.7.3.
Upvotes: 1
Views: 93
Reputation: 7473
As Johannes Schaub - litb explains in his answer to my recent question:
A alias template is not a template alias (despite intended by some to be).
So it is not a bug, it is a standard-compliant behavior.
See also paragraph [temp.alias] 14.5.7/2 of the standard:
[ Note: An alias template name is never deduced. — end note ]
Upvotes: 1
Reputation: 217135
You may do the following:
namespace detail
{
template <typename T> struct Adder
{
double operator() (double) const {
std::cerr << "Undefined for type: " << typeid(T).name() << std::endl;
exit(EXIT_FAILURE);
}
};
template <typename T> struct Adder<MyOps<T>>
{
double operator() (double x) const {
return MyOps<T>::add(x, 1.);
}
};
}
template <template <typename> class T>
double add1(double const & x) {
return detail::Adder<T<double>>()(x);
}
Upvotes: 0