SFINAE可以添加模板问题

时间:2010-01-15 05:47:52

标签: c++ templates sfinae

我正在尝试编写一个SFINAE模板,以确定是否可以将两个类一起添加。这主要是为了更好地理解SFINAE的工作原理,而不是出于任何特定的“现实世界”原因。

所以我想出的是

#include <assert.h>

struct Vec
{
  Vec operator+(Vec v );
};

template<typename T1, typename T2>
struct CanBeAdded
{
  struct One { char _[1]; };
  struct Two { char _[2]; };

  template<typename W>
  static W make();

  template<int i>
  struct force_int { typedef void* T; }; 

  static One test_sfinae( typename force_int< sizeof( make<T1>() + make<T2>() ) >::T );
  static Two test_sfinae( ... );

  enum { value = sizeof( test_sfinae( NULL ) )==1 };
};


int main()
{
  assert((CanBeAdded<int, int>::value));
  assert((CanBeAdded<int, char*>::value));
  assert((CanBeAdded<char*, int>::value));
  assert((CanBeAdded<Vec, Vec>::value));
  assert((CanBeAdded<char*, int*>::value));
}

这将编译除最后一行之外的所有行,这将给出

finae_test.cpp: In instantiation of ‘CanBeAdded<char*, int*>’:
sfinae_test.cpp:76:   instantiated from here
sfinae_test.cpp:40: error: invalid operands of types ‘char*’ and ‘int*’ to binary ‘operator+’

所以这个错误是我所期望的,但我希望编译器然后找到test_sfinae(...)定义并使用它而不是抱怨那个不解析的错误

显然我错过了什么,我只是不知道它是什么。

1 个答案:

答案 0 :(得分:4)

在我看来,您遇到了Core Issue 339以及N2634中讨论过的问题。最重要的是,你正在推动任何编译器当前可以处理的内容,即使标准允许你正在做的事情。 C ++ 0x将添加更多有关SFINAE失败和不会导致硬错误的信息。如果你想了解血腥细节,请参见N3000,§14.9.2。