Is it possible to write a C ++ template to check for the existence of a constructor?

This question in spirit is a continuation of this question from another user who has some excellent answers: Is it possible to write a template to check for the existence of a function?

I want to do exactly what is described in this question, except that I want to be able to do this for the constructor. For example, given these two types:

class NormalType
{
public:
    NormalType()
    {
        std::cout << "NormalType::NormalType()" << std::endl;
    }
};

class SpecialType
{
public:
    SpecialType()
    {
        std::cout << "SpecialType::SpecialType()" << std::endl;
    }
    SpecialType(int someArg)
    {
        std::cout << "SpecialType::SpecialType(int someArg)" << std::endl;
    }
};

And this helper function for building the object:

template<class T>
class ConstructHelper
{
public:
    template<bool HasSpecialConstructor>
    static T Construct()
    {
        return T();
    }
    template<>
    static T Construct<true>()
    {
        return T(int(42));
    }
};

I want to write code as follows:

NormalType normalType = ConstructHelper<NormalType>::Construct<has_special_constructor<NormalType>::value>();
SpecialType specialType = ConstructHelper<SpecialType>::Construct<has_special_constructor<SpecialType>::value>();

If the desired results are what is being called NormalType::NormalType(), and being called SpecialType::SpecialType(int someArg). The missing component here is that critical helper has_special_constructorthat can determine if our special constructor exists for a given type.

, , , , . , , ++ (12.1.10). , , SFINAE decltype . , , , Visual Studio 2013, SFINAE ++ 11 "Visual Studio 14" , SFINAE , :

template<class T>
struct has_special_constructor
{
    template<class S>
    struct calculate_value: std::false_type {};
    template<>
    struct calculate_value<decltype(T(int(42)))>: std::true_type {};

    static const bool value = calculate_value<T>::value;
};

VS2013, , , - SFINAE. , , , , , . - , ?

, , :

  • has_special_constructor<T>::value .

  • Visual Studio 2013, . , ++ 11 , -, .

  • - , ++ 03 (IE, - ++ 11), , ++ 11.

  • MSVC , , , ++ 11.

+4
1
template<class T>
using has_special_constructor = std::is_constructible<T, int>;

"++ 03":

template <class T>
struct has_special_constructor {
  typedef char one;
  typedef struct { char _[2];} two;

  template <std::size_t>
  struct dummy {};

  template<class U>
  static one f(dummy<sizeof(U(42))>*);
  template<class>
  static two f(...);

  static const bool value = sizeof(f<T>(0)) == sizeof(one);
};

g ​​++ 4.4 ++ 03. "++ 03" , SFINAE, ++ 03, -, ++ 03 , , ++ 11 (GCC 4.4 2009 ), , "" ++ 03 ...

+7

All Articles