Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/160.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 如何使用std::vector<;独特的_ptr<;T>&燃气轮机;作为默认参数 编辑2: 澄清:_C++_Vector_Unique Ptr_Default Parameters - Fatal编程技术网

C++ 如何使用std::vector<;独特的_ptr<;T>&燃气轮机;作为默认参数 编辑2: 澄清:

C++ 如何使用std::vector<;独特的_ptr<;T>&燃气轮机;作为默认参数 编辑2: 澄清:,c++,vector,unique-ptr,default-parameters,C++,Vector,Unique Ptr,Default Parameters,这个问题源于一个实际上与默认参数本身无关的问题,而是复制和移动构造函数。 我接受了真正回答问题的答案(因此,如果你是因为问题标题而在这里,请阅读它),并将解释为什么它最初对我不起作用 出了什么问题? 因此,如“编辑:”下所述,问题实际上相当简单: 对包含std::vector的类的赋值将破坏VisualStudio 2013中的编译(未使用其他版本进行测试),错误消息极其隐晦 评论中的假设是VC编译器有一个bug,试图调用一个不存在的复制构造函数 妈的,现在怎么办? 这个假设事实上是正确的,但不

这个问题源于一个实际上与默认参数本身无关的问题,而是复制和移动构造函数。 我接受了真正回答问题的答案(因此,如果你是因为问题标题而在这里,请阅读它),并将解释为什么它最初对我不起作用

出了什么问题? 因此,如“编辑:”下所述,问题实际上相当简单:

对包含
std::vector
的类的赋值将破坏VisualStudio 2013中的编译(未使用其他版本进行测试),错误消息极其隐晦

评论中的假设是VC编译器有一个bug,试图调用一个不存在的复制构造函数

妈的,现在怎么办? 这个假设事实上是正确的,但不是我第一次理解它的意思

实际上,VCC确实尝试调用
MyClass
的move构造函数,它隐式地定义了该构造函数。但是,这就是问题所在,它没有正确地定义它:

当显式定义move构造函数
MyClass(MyClass&&a)
时,我们实际上可以通过这样编写代码来模拟编译器的行为:

MyClass(MyClass && a)
    : foos_(a.foos_)
{}
MyClass(vector<unique_ptr<Foo>> foos) :
    foos_(std::move(foos))
{};
使用此代码生成的错误消息与使用隐式定义的错误消息完全相同,我猜 您可以立即看到这里的错误:这个move构造函数实际上试图调用
foos\uu
的复制构造函数,这当然是不可能的,因为它反过来又不能为其内容调用复制构造函数,因为它们属于
std::unique\u ptr
类型,由于明显的原因没有复制构造函数

当使用此代码时

MyClass(MyClass && a)
    : foos_(std::move(a.foos_))
{}
一切都很顺利,因为现在调用了
std::vector
的move构造函数,从而调用了其内容的move构造函数

那该怪谁呢? 可能性1: 它实际上是一个编译器错误,源于模板解决问题

如果需要,编译器希望隐式定义一个move构造函数,如果类定义中存在不可复制的类型,并且代码中曾经对该类进行过赋值,编译器就会这样做

如果满足这两个条件,它将继续定义move构造函数,但现在似乎并不关心
std::vector
模板的实际类型,只关心类本身,类本身确实定义了一个副本
构造函数,因此VCC尝试使用它,由于
std::unique\u ptr`中缺少复制构造函数,因此失败

或者,它只是完全跳过move构造函数的定义,并尝试使用copy构造函数,这会导致相同的错误

可能性2: Microsoft STL实现中有些可疑之处。这只是一个线索,我无法解释它到底是如何工作的,但对我来说这似乎是一种可能性

如何避免这种混乱? 很简单,如上所示定义自己的移动构造函数


编辑: 这似乎归结为一个特定的问题,原始答案发布在下面。 在Visual Studio(2013)中,创建一个新的Win32控制台应用程序,不要更改任何设置,并将其设置为您的主
.cpp

// ConsoleApplication2.cpp : Defines the entry point for the console application.
//

#include "stdafx.h"

#include <vector>
#include <memory>

class Foo { };

class MyClass
{
public:
    MyClass(std::vector<std::unique_ptr<Foo>> foos) :
        foos_(std::move(foos))
    {};

    std::vector<std::unique_ptr<Foo>> foos_;
};

int _tmain(int argc, _TCHAR* argv[])
{
    auto test = MyClass(std::vector<std::unique_ptr<Foo>>()); //remove this, and all works fine!
    return 0;
}
但不幸的是,这不起作用。我不知道为什么,如果有人能解释一下就好了

接下来的两次尝试是解决方法,不是实际的默认参数:

MyClass() :
    foos_() //or foos_(vector<unique_ptr<Foo>>())
{};
所以我猜这真的是关于我在初始化时犯了一个巨大的错误

另外,我正在VS2013上编译

整个错误是:

GameObject.cpp
1>c:\program files (x86)\microsoft visual studio 12.0\vc\include\xmemory0(593): error         C2280: 'std::unique_ptr<int,std::default_delete<_Ty>>::unique_ptr(const std::unique_ptr<_Ty,std::default_delete<_Ty>> &)' : attempting to reference a deleted function
1>          with
1>          [
1>              _Ty=int
1>          ]
1>          c:\program files (x86)\microsoft visual studio 12.0\vc\include\memory(1486) : see declaration of 'std::unique_ptr<int,std::default_delete<_Ty>>::unique_ptr'
1>          with
1>          [
1>              _Ty=int
1>          ]
1>          c:\program files (x86)\microsoft visual studio 12.0\vc\include\xmemory0(592) : while compiling class template member function 'void std::allocator<_Ty>::construct(_Ty *,const _Ty &)'
1>          with
1>          [
1>              _Ty=std::unique_ptr<int,std::default_delete<int>>
1>          ]
1>          c:\program files (x86)\microsoft visual studio 12.0\vc\include\xmemory0(723) : see reference to function template instantiation 'void std::allocator<_Ty>::construct(_Ty *,const _Ty &)' being compiled
1>          with
1>          [
1>              _Ty=std::unique_ptr<int,std::default_delete<int>>
1>          ]
1>          c:\program files (x86)\microsoft visual studio 12.0\vc\include\type_traits(572) : see reference to class template instantiation 'std::allocator<_Ty>' being compiled
1>          with
1>          [
1>              _Ty=std::unique_ptr<int,std::default_delete<int>>
1>          ]
1>          c:\program files (x86)\microsoft visual studio 12.0\vc\include\vector(650) : see reference to class template instantiation 'std::is_empty<_Alloc>' being compiled
1>          with
1>          [
1>              _Alloc=std::allocator<std::unique_ptr<int,std::default_delete<int>>>
1>          ]
1>          c:\users\felix\source\repos\infinite whitewursht\infinitewhitewursht\infinitewhitewursht\gameobject.h(47) : see reference to class template instantiation 'std::vector<std::unique_ptr<int,std::default_delete<_Ty>>,std::allocator<std::unique_ptr<_Ty,std::default_delete<_Ty>>>>' being compiled
1>          with
1>          [
1>              _Ty=int
1>          ]
GameObject.cpp
1> c:\program files(x86)\microsoft visual studio 12.0\vc\include\xmemory0(593):错误C2280:“std::unique\u ptr::unique\u ptr(const std::unique\u ptr&”):尝试引用已删除的函数
1> 与
1>          [
1> _Ty=int
1>          ]
1> c:\ProgramFiles(x86)\microsoft visual studio 12.0\vc\include\memory(1486):请参阅“std::unique\u ptr::unique\u ptr”的声明
1> 与
1>          [
1> _Ty=int
1>          ]
1> c:\ProgramFiles(x86)\microsoft visual studio 12.0\vc\include\xmemory0(592):编译类模板成员函数“void std::allocator::construct(_Ty*,const _Ty&)”时
1> 与
1>          [
1> _Ty=std::unique_ptr
1>          ]
1> c:\ProgramFiles(x86)\microsoft visual studio 12.0\vc\include\xmemory0(723):请参阅正在编译的函数模板实例化“void std::allocator::construct(_Ty*,const _Ty&)”的参考
1> 与
1>          [
1> _Ty=std::unique_ptr
1>          ]
1> c:\ProgramFiles(x86)\microsoft visual studio 12.0\vc\include\type_traits(572):请参阅正在编译的类模板实例化“std::allocator”的参考
1> 与
1>          [
1> _Ty=std::unique_ptr
1>          ]
1> c:\ProgramFiles(x86)\microsoft visual studio 12.0\vc\include\vector(650):请参阅正在编译的类模板实例化“std::is_empty”的参考
1> 与
1>          [
1> _Alloc=std::分配器
1>          ]
1> c:\users\felix\source\repos\infinite whitewursht\infinitewhitewursht\infinitewhitewursht\gameobject.h(47):请参阅正在编译的类模板实例化“std::vector”的参考
1> 与
1>          [
1> _Ty=int
1>          ]

编写构造函数重载,该重载不接受任何向量,并在默认情况下初始化向量(为空向量):


确切的错误是什么?(1)
因为分配给unique_ptrs绝对不是“不可能的”;(2) 使用
=
的构造不是“赋值”;(3) 移动可能是performed@0x499602D2这家伙:
Error 1 Error C2280:'std::unique\u ptr::unique\u ptr(const std::unique\u ptr&'):试图引用已删除的函数c:\program files
MyClass() :
    foos_() //or foos_(vector<unique_ptr<Foo>>())
{};
vector<unique_ptr<GameObject>> foos_;
GameObject.cpp
1>c:\program files (x86)\microsoft visual studio 12.0\vc\include\xmemory0(593): error         C2280: 'std::unique_ptr<int,std::default_delete<_Ty>>::unique_ptr(const std::unique_ptr<_Ty,std::default_delete<_Ty>> &)' : attempting to reference a deleted function
1>          with
1>          [
1>              _Ty=int
1>          ]
1>          c:\program files (x86)\microsoft visual studio 12.0\vc\include\memory(1486) : see declaration of 'std::unique_ptr<int,std::default_delete<_Ty>>::unique_ptr'
1>          with
1>          [
1>              _Ty=int
1>          ]
1>          c:\program files (x86)\microsoft visual studio 12.0\vc\include\xmemory0(592) : while compiling class template member function 'void std::allocator<_Ty>::construct(_Ty *,const _Ty &)'
1>          with
1>          [
1>              _Ty=std::unique_ptr<int,std::default_delete<int>>
1>          ]
1>          c:\program files (x86)\microsoft visual studio 12.0\vc\include\xmemory0(723) : see reference to function template instantiation 'void std::allocator<_Ty>::construct(_Ty *,const _Ty &)' being compiled
1>          with
1>          [
1>              _Ty=std::unique_ptr<int,std::default_delete<int>>
1>          ]
1>          c:\program files (x86)\microsoft visual studio 12.0\vc\include\type_traits(572) : see reference to class template instantiation 'std::allocator<_Ty>' being compiled
1>          with
1>          [
1>              _Ty=std::unique_ptr<int,std::default_delete<int>>
1>          ]
1>          c:\program files (x86)\microsoft visual studio 12.0\vc\include\vector(650) : see reference to class template instantiation 'std::is_empty<_Alloc>' being compiled
1>          with
1>          [
1>              _Alloc=std::allocator<std::unique_ptr<int,std::default_delete<int>>>
1>          ]
1>          c:\users\felix\source\repos\infinite whitewursht\infinitewhitewursht\infinitewhitewursht\gameobject.h(47) : see reference to class template instantiation 'std::vector<std::unique_ptr<int,std::default_delete<_Ty>>,std::allocator<std::unique_ptr<_Ty,std::default_delete<_Ty>>>>' being compiled
1>          with
1>          [
1>              _Ty=int
1>          ]
MyClass() : foos_{}
{}