Constructor C ++ SFINAE

#include <iostream>

using namespace std;

template <typename T>
class test {
public:
    T value;

    template <typename... Args, typename = decltype(T())>
    test(Args... args): value(args...)
    {
       cout <<"ctor running\n";
    }

    template <typename... Args>
    test(Args...) : value(1)
    {
       cout <<"ctor unspec  running\n";
    }
};


class t
{
public:
    t() = delete;
    explicit t(int) {}
};


int main()
{
    test<t> h;
}

I am trying to call the second constructorfor the created object ( h). I do not know why I am getting this error:

prog.cc: In function 'int main()':
prog.cc:45:13: error: call of overloaded 'test()' is ambiguous
     test<t> h;
             ^
prog.cc:25:5: note: candidate: 'test<T>::test(Args ...) [with Args = {}; T = t]'
     test(Args... args)
     ^~~~
prog.cc:19:5: note: candidate: 'test<T>::test(Args ...) [with Args = {}; <template-parameter-2-2> = t; T = t]'
     test(Args... args): value(args...)
     ^~~~

I tried to do everything class t private, but that also did not fix it. I want to run the second constructor, i.e. Print `

"ctor unspec running"

What am I missing here? The first call constructorshould be SFINAed, because it typename = decltype(T())does not work, because tit cannot be default constructed, but instead I get a call error ambiguous.

+4
source share
1 answer

SFINAE . T , , . , "" . , , constuctor, .

, , T, SFINAE:

template <typename... Args, typename U = T, typename = decltype(U{})>
test(Args... args): value(args...)
{
   cout <<"ctor running\n";
}

U , SFINAE.

SFINAE . "", , , "", . :

template <typename... Args, typename U = T,
    std::enable_if_t<!std::is_default_constructible<U>::value>* = nullptr>
test(Args...) : value(1)
{
   cout <<"ctor unspec  running\n";
}

+4

Source: https://habr.com/ru/post/1691213/


All Articles