For循环迭代不断增长的向量

Posted

技术标签:

【中文标题】For循环迭代不断增长的向量【英文标题】:For loop iterating over growing vector 【发布时间】:2015-02-05 10:40:39 【问题描述】:

我的问题是,总是下面的 for 循环只迭代一次。

在进入循环之前,search_list 的大小始终为 1。但是 search_list 向量可能会在循环内增长,并且应该分别迭代以防某些元素添加到列表中。

   std::vector<int> search_list;
   search_list.clear();
   search_list.push_back(first_elem);

   for(auto &discover : search_list)
   
       ......
       if(&std::find(face_ids.begin(), face_ids.end(), i))
       
           search_list.push_back(i);
       
       ......
   

如何使这个 for 循环根据不断增长的向量进行多次迭代?即使某些内容被推送到搜索列表,它也不会重复多次。如果添加了某些东西,它应该将发现设置为该元素并重新进入循环。

【问题讨论】:

你的代码还能编译吗?顺便说一句,搜索 face_ids,生成一个临时向量,然后一次性插入到 search_list 中。 实际上并不清楚您想要实现什么(如果已添加元素或仅将该元素添加到循环中,则从头开始重新启动循环,或者什么?)。在 for 循环范围内添加或删除向量元素会带来麻烦,而且很可能是未定义的。 只要一个新元素被推送到 search_list 向量,我希望这个循环继续迭代。 @Caner - 附带问题 -- &amp;std::find(face_ids.begin(), face_ids.end(), i) 解释您在这里尝试做什么,尤其是使用 &amp; @Caner “我希望这个循环只要有新元素被推送就一直迭代”。这不是您要解决的问题。那是您为解决最初的问题而创建的问题。人们问你你的初始问题是什么,因为这看起来很奇怪,这无助于你隐藏了大部分函数体,我们不知道ì来自哪里。这里可能有更好的设计方法,但我们需要更多的上下文。 【参考方案1】:

您的问题是迭代器是在您开始循环时创建的,但随后没有更新。 您应该对索引执行 for 循环:

std::vector<int> search_list;
search_list.clear();
search_list.push_back(first_elem);

for (int ii=0 ; ii < search_list.size() ; ii++) 
       ......
       if(&std::find(face_ids.begin(), face_ids.end(), i))
       
           search_list.push_back(i);
       
       ......

这样,如果添加了一个元素,search_list.size() 将会增长并且循环将继续,因为它每次都会调用它。

请注意,如果始终验证 if 语句,则会产生无限循环。

编辑:根据 Félix Cantournet 的建议,这是一个带有while 循环和一些不能无限运行的控制的版本

int max_it = 1000;
int ii=0;
...
// i = MAGIC
...
while (&std::find(face_ids.begin(), face_ids.end(), i) && ii < max_it) 
       search_list.push_back(i);
       ......
       // i = NEW MAGIC
       ......
       ii++;

【讨论】:

好吧,如果您要进行潜在的无限循环(您就是这样),我建议您使用带有布尔条件的while。我认为while(condition) 在“警告这可能是无限的”上更加明确。在不相关的旁注中:必须有某种方法可以在没有潜在无限循环的情况下执行 OP 想要执行的操作。 @FélixCantournet 这取决于.... 中的操作。如果i 在每个循环中都是唯一的,那么它就不是无限的,因为face_ids 的大小是有限的(除非它也被更改,但代码真的应该重新考虑) 是的,我同意,它只是“潜在”无限,但我仍然一点也不喜欢这种设计。特别是因为事情只被推入search_list if i is found in face_ids,我认为这应该是while循环的条件。离开search_list.size() 对我的最后一条评论进行更多衡量:如果不知道i 的值的生成,很难选择正确的实现。【参考方案2】:

对容器执行添加或删除元素或调整大小的操作可能会使该容器的所有迭代器失效。

基于范围的 for 循环假定迭代器没有失效,因此如果它们失效,则会给出未定义的行为。本质上,您需要使用传统的循环。如果容器被调整大小,则断开并重新启动外循环(例如,将您的外循环放在另一个循环中,根据需要继续运行)。

这通常涉及重构您的代码,但通常情况下,避免在对同一容器进行迭代的循环中调整容器大小会更安全。在实践中很少有这种情况是不可能的。

【讨论】:

【参考方案3】:

问题在于,您不仅更改了循环内列表的end(这会使基于范围的 for 循环的使用无效),而且还可能使列表的所有iterators 无效(这会使iterator 基于 for 循环。

因此,您必须求助于不会失效的东西。唯一符合这个要求的是索引。就像数学的答案一样。

但是,这意味着您的算法特定于使用 vector 而不是 list(当您仍然可以使用基于 iterator 的 for 循环时)。

【讨论】:

以上是关于For循环迭代不断增长的向量的主要内容,如果未能解决你的问题,请参考以下文章

使用 for 循环迭代空矩阵

python中for循环的底层实现机制 迭代

For-Loop一个带有负迭代器的“空”向量?

Python - for循环的本质

OpenMP 并行 for 循环异常

for循环最后一次迭代的指针变化