我是一名程序员,在进行更改并学会避免STL时学习了C++.相反,我使用了MFC容器类和我可能使用的框架可用的任何容器类.
我也从未真正使用智能指针.8)
所以,我正在研究C++中的新功能(使用VS 2013)
以下编译和工作正常:
vector<string> names;
names.push_back("tom");
names.push_back("dick");
names.push_back("harry");
names.push_back("bob");
names.push_back("percy");
names.push_back("freddie");
names.push_back("sam");
for (auto name : names)
{
cout << "Name: " << name << endl;
}
Run Code Online (Sandbox Code Playgroud)
以下不是:
vector<unique_ptr<Thing>> things;
things.push_back(unique_ptr<Thing>(new Thing("tom", 23)));
things.push_back(unique_ptr<Thing>(new Thing("dick", 26)));
things.push_back(unique_ptr<Thing>(new Thing("harry", 33)));
things.push_back(unique_ptr<Thing>(new Thing("fred", 43)));
things.push_back(unique_ptr<Thing>(new Thing("bob", 53)));
for (auto thing : things)
{
}
Run Code Online (Sandbox Code Playgroud)
我收到以下错误消息:
1>c:\dev\src\samples\consoletest\consoletest\vectorstuff.cpp(34): error C2280: 'std::unique_ptr<Thing,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=Thing
1> ]
1> c:\program files (x86)\microsoft visual studio 12.0\vc\include\memory(1486) : see declaration of 'std::unique_ptr<Thing,std::default_delete<_Ty>>::unique_ptr'
1> with
1> [
1> _Ty=Thing
1> ]
Run Code Online (Sandbox Code Playgroud)
所以我尝试了标准迭代器:
for (auto thing = things.begin(); thing != things.end(); ++thing)
{
cout << "Name: " << (*thing)->getName() << " age: " << (*thing)->getAge() << endl;
}
Run Code Online (Sandbox Code Playgroud)
哪个编译好,那么为什么for(auto thing:things)语法不起作用?
这是我对Thing的定义:
class Thing
{
public:
Thing();
Thing(const Thing& original);
Thing(const std::string& name, int age);
const std::string& getName() const { return name; }
int getAge() const { return age; }
private:
std::string name;
int age;
};
Run Code Online (Sandbox Code Playgroud)
和代码:
Thing::Thing() : name(""), age(21)
{
}
Thing::Thing(const Thing& original) : name(original.name), age(original.age)
{
}
Thing::Thing(const std::string& name, int age) :
name(name),
age(age)
{
}
Run Code Online (Sandbox Code Playgroud)
我添加了默认构造函数和复制构造函数,但仍然获取了已删除的函数.
auto thing : things按值复制,禁用unique_ptr.而是使用:
auto &thing : things
Run Code Online (Sandbox Code Playgroud)
这种情况与基于迭代器的循环之间的区别在于,在这种情况下,auto thing是根据auto thing = *begin;(参见此处获取更多信息)定义的.
但是在你写的情况下auto thing = things.begin();, thing实际上是一个迭代器,所以一切都很好.
auto thing : things表示thing每次迭代的值是元素的副本things.如果类型不可复制(unique_ptr不是),那么这将不起作用.
相反,请thing参考:
for (auto & thing : things) // add "const" if appropriate
Run Code Online (Sandbox Code Playgroud)