[英]C++ standard template library vector question
Can someone explain in English what is going on here? 有人可以用英语解释这里发生了什么吗?
std::vector<Cat*> cats; //I get that cats is a vector of Cat objects
if (std::find(cats.begin(), cats.end(), morris) == cats.end()) {
cats.push_back(morris);
}
@mlimber has already given one explanation. @mlimber已经给出了一种解释。
I'd explain it a bit differently. 我会以不同的方式解释它。 In plain English, it's a way of taking something really simple:
用简单的英语来说,这是一种非常简单的方法:
std::set<Cat> cats;
cats.insert(morris);
and making it slower (linear instead of logarithmic) and considerably harder to read or understand. 并使其变慢(线性而不是对数),并且难以阅读或理解。
Edit: In fairness, I suppose I should add that there are a few reasons you might want to do something like this. 编辑:凭心而论,我想我要补充一点, 还有你可能想要做这样的事情的几个原因。 For example, if you really need to know the order in which
Cat
s were added to the collection, preserving the original order might make some sense. 例如,如果您确实需要知道将
Cat
添加到集合中的顺序,那么保留原始顺序可能会有些道理。 Likewise, if you're usually using the collection in a way that benefits from them being contiguous in memory, and only rarely adding a new item, it might make more sense to store the data in a vector
than an set
. 同样,如果通常使用集合的方式是受益于它们在内存中是连续的,并且很少添加新项目,那么将数据存储在
vector
比set
更有意义。
A set
, however, is designed to do exactly what's being done here, so a set
is the obvious choice (absent compelling reasons to use a vector
that just aren't visible in what you've shown). 但是,
set
目的是完全执行此处要做的事情,因此set
是显而易见的选择(没有明显的理由使用在显示的内容中不可见的vector
)。
It adds an item called morris
to the vector cats
IF the vector doesn't already has it! 如果媒介
cats
还没有的话,它将在媒介cats
添加一个名为morris
的物品!
The std::find
is used to check if the item morris
is in the vector cats
or not. std::find
用于检查morris
项目是否在矢量cats
。 It doesn't has, std::find
returned value would be equal to cats.end()
. 它没有,
std::find
返回的值将等于cats.end()
。 After this, everything else is pretty much straight forward. 在此之后,其他一切都非常简单。
假设代码是正确的(例如morris的类型和初始化,并使用指针进行比较),重点是看morris是否在猫的集合中,如果不是,则将其添加到猫中。
cats is a vector of pointers to Cat objects, not a vector of Cat objects. cats是指向Cat对象的指针的向量,而不是Cat对象的向量。
This searches the full range of cats(cats.begin() through cats.end()) for an object(pointer to cat) that is equal to morris 这会在cats(cats.begin()到cats.end())的整个范围内搜索等于morris的对象(指向cat的指针)
std::find(cats.begin(), cats.end(), morris)
The return value is an iterator into the vector pointing to the object if it was found, and it returns the end iterator(cats.end()) if it was not found. 返回值是指向对象的向量中的迭代器(如果找到),如果未找到,则返回结束iterator(cats.end())。 With that in mind, this:
考虑到这一点,这是:
if (std::find(cats.begin(), cats.end(), morris) == cats.end())
is a test to see if cats contains that object(morris). 测试猫是否包含该对象(莫里斯)。 And if it doesn't, then it executes this:
如果没有,它将执行以下命令:
cats.push_back(morris);
which puts the object(morris), into the vector. 将对象(morris)放入向量中。
First be carefull : your comment is wrong. 首先要小心:您的评论是错误的。 cats isn't a vector of Cat objects, but a vector of POINTERS to cat objects.
cat不是Cat对象的向量,而是POINTERS对cat对象的向量。
Now, the statement : 现在,声明:
std::find(cats.begin(), cats.end(), morris) std :: find(cats.begin(),cats.end(),莫里斯)
implies you have a Cat* somewhere called morris. 表示您在某处有莫里斯猫*。 This statement is going to search the vector, between the two provided iterators (ie : cats.begin() and cats.end() ) for a pointer to Cat, equall to morris (same address).
该语句将在两个提供的迭代器(即cats.begin()和cats.end())之间搜索向量,以寻找指向Cat的指针,该指针等于morris(相同的地址)。 If none is found, std::find returns the second iterator, so, in your case "cats.end()"
如果未找到,则std :: find返回第二个迭代器,因此,在您的情况下为“ cats.end()”
Therefore "if (std::find(cats.begin(), cats.end(), morris) == cats.end()) { cats.push_back(morris); }" means, in plain english "if morris isn't already in the cats vector, put it at the end" 因此,“ if(std :: find(cats.begin(),cats.end(),莫里斯)== cats.end()){cats.push_back(morris);}”的意思是,用简单的英语“如果morris不是不在猫咪矢量中,放在最后”
I'll have a hard time being more specific if we don't know what's bothering you exactly 如果我们不知道到底是什么困扰着我,我会很难说清楚
std::vector<Cat*> cats; //I get that cats is a vector of Cat objects
You get that wrong. 你说错了。
cats
is a std::vector
of pointers to the class Cat
. cats
是指向Cat
类的指针的std::vector
。 There's a difference: Cat
s reside on the stack, are created by doing 区别在于:
Cat
驻留在堆栈中,是通过以下方式创建的
Cat morris;
and do not have to be deleted. 并且不必删除。 Pointers as in your example, are created by
如您的示例中的指针是由
Cat* morris = new Cat();
and have to be deleted once you're done with it before you throw away the pointer: 并在删除指针后必须将其删除:
delete morris;
I will now add a little code to your example: 现在,我将向您的示例添加一些代码:
Cat* morris = new Cat();
if (std::find(cats.begin(), cats.end(), morris) == cats.end()) {
cats.push_back(morris);
}
This creates a dynamically allocated object morris
of type Cat
on the heap. 这将在堆上创建
Cat
类型的动态分配对象morris
。 Then, std::find
is used to search the vector cats
for the newly created object, which will always fail in this code fragment. 然后,
std::find
用于搜索的矢量cats
为新创建的对象,这将始终在这段代码失败。 If std::find
fails, it returns an iterator to the element one past the last element in the container (which is exactly what std::vector::end()
returns). 如果
std::find
失败,它将向容器中最后一个元素之后的元素返回一个迭代器(这正是std::vector::end()
返回的结果)。 So if morris
is not found, the code will create a new element at the back of the vector and add morris
to it. 因此,如果未找到
morris
,则代码将在向量的后面创建一个新元素,并向其中添加morris
。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.