1週間前に、クラステンプレートが特定のメンバー関数を持っていた場合にのみ、クラステンプレートをどのようにインスタンス化できるかを質問しました。私の答えでは、私は複雑な解決策の一種を持っています。しかし、私は自分でそれをやろうとしました。私はちょうど与えられたタイプT
を把握するのに十分なものが0のパラメータを取るf
という名前のvoid関数を持っているかどうかを知りたいと思っていました。これはSFINAEとは考えられますか?
#include <type_traits>
#include <utility>
template <typename T, typename = void>
struct has_f : std::false_type { };
template <typename T>
struct has_f<
T,
decltype(std::declval<T>().f(), void())> : std::true_type { };
template <typename T, typename = typename std::enable_if<has_f<T>::value>::type>
struct A { };
struct B
{
void f();
};
struct C { };
template class A<B>; // compiles
template class A<C>; // error: no type named ‘type’
// in ‘struct std::enable_if<false, void>’
もしそうなら、なぜ他の回答がthis thread?
を使用するには。なぜ他の答えがより複雑になっているのかは分かりません。 –
'has_f'自体がSFINAEに依存していることを明確にするため、' A'はそうではありません。 –
可能性として、SFINAEはいくつかのコンパイラ(* cough * MSVC2012)のサックをサポートしているので、その複雑さのいくつかは、より移植性の高いSFINAEを持つための回避策かもしれません。 'std :: declval()'?)()のように、 'std :: declval ().f()'と 'std :: declval () 'this'機能へのrvalue参照のため、C++ 1yではさまざまなことがあります。 –
Yakk