Ошибка привязки make_unique

У меня проблемы с использованием std::bind с std::make_unique,

У меня есть объект, в конструктор которого я передаю фабричные функции для создания std::unique_ptrс объектов другого типа класса.

Используя VS2013, это работает:

Tester tester( 
    [](){return std::make_unique<AlphaBetaSingleThreadSSE>( 0,7 ); },
    [](){return std::make_unique<AlphaBetaSingleThread>( 0,7 ); },
    20 );

Это дает мне ошибки компиляции:

Tester tester( 
    std::bind( std::make_unique<AlphaBetaSingleThreadSSE>,0,7 ),
    std::bind( std::make_unique<AlphaBetaSingleThread>,0,7 ),
    20 );

Состояние сообщений об ошибках:

ошибка C2512: "AlphaBetaSingleThread": не доступен соответствующий конструктор по умолчанию

ошибка C2512: "AlphaBetaSingleThreadSSE": не доступен соответствующий конструктор по умолчанию

Почему std::bind сбой подхода?

1 ответ

Решение

std::make_unique определяется следующим образом:

§ 20.8.1.4 [unique.ptr.create]

template <class T, class... Args> unique_ptr<T> make_unique(Args&&... args);

1 Примечание: эта функция не должна участвовать в разрешении перегрузки, если только T это не массив.

2 Возвращает: unique_ptr<T>(new T(std::forward<Args>(args)...)).

Путем явного создания экземпляра этого шаблона функции с std::make_unique<AlphaBetaSingleThreadSSE> Вы получаете следующую специализацию:

std::unique_ptr<AlphaBetaSingleThreadSSE> make_unique()
{
    return std::unique_ptr<AlphaBetaSingleThreadSSE>(new AlphaBetaSingleThreadSSE());
}

То есть он больше не позволит передавать дополнительные аргументы, которые будут перенаправлены в конструктор AlphaBetaSingleThreadSSEи вместо этого попытается использовать конструктор по умолчанию AlphaBetaSingleThreadSSE (который не существует, как говорится в сообщении об ошибке).

Вы можете обойти это, указав также параметр типа шаблона Args:

std::make_unique<AlphaBetaSingleThreadSSE, const int&, const int&>

но тогда вам не удастся извлечь выгоду из совершенной пересылки, и это не переносимое решение в любом случае. Лучшее решение - остаться с лямбдой.

Другие вопросы по тегам