I am trying to use std::enable_if to specialize a class if one of its subclasses has a specific member function. Otherwise, it should use the default implementation, which is defined in the base class.
#include <boost/mpl/list.hpp> #include <boost/function_types/function_type.hpp> #include <boost/tti/has_member_function.hpp> #include <iostream> #include <type_traits> #include <memory> BOOST_TTI_HAS_MEMBER_FUNCTION(f2) class Base { public: virtual double f1(double x, double y) const { std::cout << "Called Base Method" << std::endl; return 0.0; } }; template<typename Derived> class A : public Base { public: template<typename T = Derived> typename std::enable_if < has_member_function_f2< T , double , boost::mpl::list<double> , boost::function_types::const_qualified >::value , double >::type f1(double x, double y) const { std::cout << "Called Derived Method" << std::endl; return static_cast<const Derived* const>(this)->f2(x); } }; class B : public A<B> { public: double f2(double x) const { return 1.0; } }; int main() { std::unique_ptr<Base> base_instance( new B ); std::cout << base_instance->f1(100.0, 10.0) << std::endl; B b_instance; std::cout << b_instance.f1(100.0, 10.0) << std::endl; return 0; }
I expected it to print
Called Derived Method 1 Called Derived Method 1
however instead i get
Called Base Method 0 Called Derived Method 1
so it looks like an object is fragmenting. For life, I cannot understand why this would be so if someone could help me, which would be very grateful.
If this helps, it compiles with g ++ 4.7.2
c ++ c ++ 11 virtual-functions enable-if object-slicing
Simon Gibbons
source share