Comportement enable_if étrange à l'aide de classes imbriquées (insecte ou fonctionnalité de compilateur MSVC?)

StackOverflow https://stackoverflow.com/questions/3209085

Question

Après un certain temps de débogage de mon code, j'ai suivi la raison de mes problèmes à des résultats de spécialisation de modèles inattendus à l'aide d'activation_if:

Le code suivant échoue à l'affirmation dans Dotest () dans Visual Studio 2010 (et 2008), alors qu'elle ne le fait pas dans G ++ 3.4.5. Cependant, lorsque je retire le modèle de soméclass ou déplacez my_condition hors de la portée de Someclass Il fonctionne également dans MSVC.

Y a-t-il un problème avec ce code qui expliquerait ce comportement (au moins partiellement) ou est-ce qu'un bogue dans le compilateur MSVC?

(en utilisant cet exemple de code, il est identique à Boost et à la version STL C ++ 0x)

#include <cassert>
#include <boost\utility\enable_if.hpp>

template <class X>
class SomeClass {
public:
    template <class T>
    struct my_condition {
        static const bool value = true;
    };

    template <class T, class Enable = void> 
    struct enable_if_tester { 
        bool operator()() { return false; }
    };

    template <class T>
    struct enable_if_tester<T, typename boost::enable_if< my_condition<T> >::type> { 
        bool operator()() { return true; }
    };

    template <class T>
    void DoTest() {
        enable_if_tester<T> test;
        assert( test() );
    }
};

int main() {
    SomeClass<float>().DoTest<int>();
    return 0;
}


Lorsque vous essayez de le réparer en déplaçant la condition hors de la portée, j'ai également remarqué que cela ne suffit même pas lorsque vous utilisez STD :: Enable_if, mais au moins cela fonctionne avec boost ::able_if:

#include <cassert>
//#include <boost\utility\enable_if.hpp>
#include <type_traits>

template <class T, class X>
struct my_condition {
    static const bool value = true;
};

template <class X>
class SomeClass {
public:
    template <class T, class Enable = void> 
    struct enable_if_tester { 
        bool operator()() { return false; }
    };

    template <class T>
    //struct enable_if_tester<T, typename boost::enable_if< my_condition<T, X> >::type> { 
    struct enable_if_tester<T, typename std::enable_if< my_condition<T, X>::value >::type> { 
        bool operator()() { return true; }
    };

    template <class T>
    void DoTest() {
        enable_if_tester<T> test;
        assert( test() );
    }
};

int main() {
    SomeClass<float>().DoTest<int>();
    return 0;
}

J'espère que quelqu'un a une explication à cela.

Était-ce utile?

La solution

Tout va bien avec votre code, c'est juste que VC est buggy.Il est connu d'avoir des problèmes de spécialisation partielle de modèles de classes de membres de modèle.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top