如何将元素从C ++ 11容器移动到容器的背面?
我特意使用列表但是如果需要可以使用向量(或者可能是任何容器;最好能获得通用的容器解决方案)。
我有一个元素列表。我有一个价值。我将此值传递给每个元素;其中一人会回应。第一个响应的我想要移动到容器的后面。
我现有的代码如下所示:
std::list<elements> m_elements
...
bool handle(event e)
{
for(auto &element : m_elements)
{
if(element->handle())
return true;
}
return false;
}
但我现在要做的是将handle()
事件的元素移到m_elements
的末尾。对于一些上下文,我正在使用Windows的GUI系统。因此,无论哪个窗口捕获鼠标,都需要在绘制时跳到顶部;正在逐一绘制m_elements
中的窗口(因此最后一个元素位于顶部)。
可能值得注意的是元素是std::shared_ptr
s。
如果有人遇到这个问题并回答类似的情况。
我实际上需要向后遍历我的容器以处理输入,因为最后一个元素是最后一个,即它位于顶部,因此它应该是应该尝试拦截输入的第一个元素。
这很简单。但是,将反向迭代器拼接到容器的末端有点棘手。如果迭代器是一个前向迭代器,std::reverse_iterator.base()
会返回NEXT迭代器,所以你需要std::advance
-1
迭代器,以便成功移动&#34;截获的实际元素&# 34。
for(auto itr = m_elements.rbegin(); itr != m_elements.rend(); ++itr)
{
if((*itr)->handle(e))
{
auto itr2 = itr.base();
std::advance(itr2,-1);
m_elements.splice(m_elements.end(), m_elements, itr2);
return true;
}
}
希望这有助于下一个可怜的灵魂。
答案 0 :(得分:8)
如果要删除元素并将其添加到最后(有效地将其他所有内容向下移动),则可以使用std::list::splice
方法执行此操作,该方法将在新位置重新链接节点,而无需任何要创建或销毁的节点。它所要做的只是调整现有节点上的节点指针以反映您想要的更改。
for (auto i = m_elements.begin(); i != m_elements.end(); ++i) {
if ((*i)->handle()) {
// Move this node to the back.
m_elements.splice(m_elements.end(), m_elements, i);
return true;
}
}
return false;
有更多通用解决方案适用于任何容器(包括std::list
),但与特定容器的技术相比,它们可能不是最佳的。