Проблем със SFINAE

Защо този код (стойност fnc в клас M) не се разрешава от правилата на SFINAE? Получавам грешка:

Error   1   error C2039: 'type' : is not a member of
                                   'std::tr1::enable_if<_Test,_Type>'  

Разбира се type не е член, не е дефиниран в тази обща версия на enable_if, но не е ли цялата идея зад това да се активира тази версия на fnc, ако bool е true и да не се инстанцира, ако е false? Може ли някой да ми обясни това?

#include <iostream>
#include <type_traits>

using namespace std;

template <class Ex> struct Null;
template <class Ex> struct Throw;

template <template <class> class Policy> struct IsThrow;

template <> struct IsThrow<Null> {
    enum {value = 0};
};

template <> struct IsThrow<Throw> {
    enum {value = 1};
};

template <template <class> class Derived>
struct PolicyBase {
    enum {value = IsThrow<Derived>::value};
};

template<class Ex>
struct Null : PolicyBase<Null> { };

template<class Ex>
struct Throw : PolicyBase<Throw> { } ;

template<template< class> class SomePolicy>
struct M {

  //template<class T>
  //struct D : SomePolicy<D<T>>
  //{
  //};
  static const int ist = SomePolicy<int>::value;
  typename std::enable_if<ist, void>::type value() const
  {
    cout << "Enabled";
  }

  typename std::enable_if<!ist, void>::type value() const
  {
    cout << "Disabled";
  }
};

int main()
{
    M<Null> m;
    m.value();
}

person There is nothing we can do    schedule 12.11.2010    source източник


Отговори (2)


SFINAE не работи за функции без шаблон. Вместо това можете напр. използвайте специализация (на класа) или базирано на претоварване диспечиране:

template<template< class> class SomePolicy>
struct M
{
    static const int ist = SomePolicy<int>::value;        
    void value() const { 
        inner_value(std::integral_constant<bool,!!ist>()); 
    }
 private:
    void inner_value(std::true_type) const { cout << "Enabled"; }
    void inner_value(std::false_type) const { cout << "Disabled"; }
};
person Georg Fritzsche    schedule 12.11.2010

Тукняма сфина.

След като M<Null> е известна, променливата ist също е известна. Тогава std::enable_if<ist, void> също е добре дефинирано. Една от вашите функции не е добре дефинирана.

SFINAE работи само в случай на шаблонни функции. Къде са функциите на шаблона?

Променете кода си на

template<int> struct Int2Type {}

void value_help(Int2Type<true> ) const { 
    cout << "Enabled"; 
} 

void value_help(Int2Type<false> ) const { 
    cout << "Disabled"; 
} 

void value() const { 
    return value_help(Int2Type<ist>());
}
person Alexey Malistov    schedule 12.11.2010