0

I'm unable to figure out why this happens. The question and comments are inline.

using DefaultType_t = void;

template<typename...>
using void_t = DefaultType_t;

template<typename T>
struct is_float;

template<>
struct is_float<float> {
  using type = float;
};

template<typename T>
using is_float_t = typename is_float<T>::type;

template<typename , typename = DefaultType_t>
struct A {
  A() {std::printf("\nCalled 0\n");}
};

template<class T>
struct A<T, void_t<is_float_t<T>>> {
  A() {std::printf("\nCalled 1\n");}
};

int main() {
  is_float_t<float> {}; // Works fine ------\\
  //                                           ==> I understand these two cases.
  is_float_t<int>   {}; // Compile Error ---//

  A<int>            {}; // Prints Called 1  <Q> Why does this not Print Called 0 ??
                        //                      Because is_float_t<int> is erroneous,
                        //                      so shouldn't SFINAE apply ?
}

So the in-lined question once again : Why does A<int> {}; not print Called 0 ? A<AnyType> would first pick up the default template parameter from the base template which happens to be DefaultType_t in this case. Then it would try to find if there is more specialized version of it. According to me there is none because the specialized one has the second template parameter ill-formed because is_float_t<int> is ill-formed. So it should just pick the base. No?

using GCC/G++ 4.8.2 on Ubuntu 14.04 {64 bits} with -std=c++11

ustulation
  • 3,600
  • 25
  • 50
  • 4
    http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_active.html#1558 – Marc Glisse Nov 01 '14 at 07:49
  • @MarcGlisse: Wow. Actually after hearing Walter Brown on CppCon I figured I could need void_t stuff in many places, but just couldn't get it to work. Now I see from your link that I need to `use` the template parameter. So doing this immediately worked: `template struct void_t_indirection { using type = DefaultType_t; };` and then `template using void_t = typename void_t_indirection::type;` – ustulation Nov 01 '14 at 08:53
  • There must be at least half a dozen CWG 1558/`void_t` questions on SO already. – T.C. Nov 01 '14 at 09:19
  • 1
    @T.C.: and hence the necessity of making something consumer friendly :) .. avg consumers being a much greater community than expert consumers. I don't even read the standard though I've a copy of it (c++11) because it's so arcane to me and when somebody in SO explains a part of the standard it is so much easier to grasp. But it's meant for smarter people and I don't mind that :) – ustulation Nov 01 '14 at 09:52

0 Answers0