Ответ 1
Нет, нет поддержки в tuple
или pair
для передачи типов невозврата их конструкторам, и, как вы заметили, не может быть, поскольку аргумент конструктора и член кортежа (или пары) можно рассматривать как разные объекты:
// exposition only
template<class... Us>
tuple(Us&&... us) : values{std::forward<Us>(us)...} {}
^^ these
^^^^^^ are different objects to these
Вам придется использовать кусочную конструкцию:
return std::pair<std::string, nocopy>(std::piecewise_construct,
std::forward_as_tuple(), std::forward_as_tuple());
Мэтт Калабрес сделал интересный момент в списке std-предложений, который теперь мы гарантировали RVO, должно быть возможно писать компоненты, которые принимают заводы эффективно создавать своих членов на месте:
// hypothetical factory constructor
return std::pair(std::factory_construct,
[] { return std::string{}; }, [] { return nocopy{}; });
Другим возможным направлением будет удаление конструкторов из tuple
и pair
(или, что более реалистично, для написания рабочих компонентов без конструкторов) и полагаться на новые расширения для агрегации инициализации, которые должны допускать агрегатную инициализацию tuple
и pair
, реализованную с помощью множественного наследования. Пример.