Незамысловатый, но подвижный контейнер
У меня есть проблема с этой программой:
struct A {};
int main()
{
::std::vector< ::std::unique_ptr<A> > v;
::std::cout << ::std::is_copy_constructible<decltype(v)>{} << ::std::endl;
//decltype(v) w(v);
return 0;
}
Выводится:
1
Однако, если я раскомментирую прокомментированную строку, программа не сможет скомпилировать. Как вы думаете, это ошибка в стандарте, что ::std::is_copy_constructible<decltype(v)>{}
оценивается как true
и где в стандарте? Следует ли, например, зафиксировать метафокус или контейнер должен удалить его конструктор копирования, если value_type
не может быть скопирован?
РЕДАКТОР: Полагаю, я должен уточнить, почему это важно. Скажем, у вас есть шаблон класса variant
, который содержит шаблон класса контейнера, созданный с помощью не скопируемого value_type
. variant
могут SFINAE
удалять методы, которые копируют контейнер и избегают ошибок компиляции, но поскольку он получает неверную информацию из STL
, он не может. В результате этой проблемы мне пришлось написать специальный шаблон класса moving_variant
, который только перемещается, никогда не копирует, тогда как он может/должен иметь один шаблон шаблона variant
.
Ответы
Ответ 1
is_copy_constructible
определяется в терминах is_constructible
, что верно, если такое выражение хорошо сформировано:
T t(create<const T&>())
В случае vector<unique_ptr>
это корректно сформировано, так как vector
объявляет подходящий конструктор копирования. Конструктор не может быть создан, поскольку он использует удаленную функцию; но шаблоны не создаются при использовании в неоценимом контексте, подобном этому.