Кортеж с неконопируемым элементом const

Мне нужно создать std::tuple<const XYZ,...> где XYZ не копируется. Возможно ли что-то подобное? Мой текущий код

auto test() -> std::tuple<const XYZ> { return std::make_tuple(XYZ()); }

приводит к C2248 в Visual Studio 2010 … Что я нахожу довольно сомнительным, так как я создаю кортеж с R-значением, поэтому я предполагаю, что конструкция move перешла бы …

4

Решение

Ваша проблема в том, что элемент не копируемый и const, const XYZ элемент ведет себя как const XYZ член; по 5.2.5p4 доступ к const XYZ элемент в xvalue даст xvalue с квалификацией union cv, то есть с эффективным типом const XYZ &&, Этот тип не подходит в качестве аргумента для конструктора перемещения XYZ поэтому вместо этого будет предпринята попытка вызова конструктора удаленных / личных копий.

Другой способ взглянуть на это состоит в том, что конструктор перемещения (например, конструктор перемещения std::tuple<...>) обязан убедиться, что его аргумент не указан, но действительный государство. Делая элемент const Вы сказали, что единственным допустимым состоянием для этого элемента является состояние, с которым он построен, поэтому конструктору перемещения не разрешено перемещаться из него, даже если он содержится в xvalue.

Обходной путь должен был бы определить постоянный ход конструктор и const_cast его аргумент для делегирования конструктору перемещения:

XYZ(const XYZ &&xyz): XYZ(const_cast<XYZ &&>(xyz)) {}

Забавно, но с gcc-4.7.2 достаточно просто объявлять конструктор const move; с помощью RVO фактический вызов конструктора const move может быть исключен. Не надейся на это.

3

Другие решения

Других решений пока нет …

По вопросам рекламы [email protected]