如何迭代列表并从中删除?

Taz*_*ngo 5 c++ iteration containers c++11

我在使用List迭代器时遇到了很多麻烦,之前我问过一个问题但是无法得到我想要的解决方案.

我有一个循环列表,我必须用节点n +替换节点n的值(步骤).然后我必须擦除节点n +(步骤).当我擦除它时,将迭代器放在擦除元素之后的元素中.我需要在节点n处返回迭代器.我怎么能这样做因为每当我擦除n +(步骤)我得到一个无效的迭代器.我的输入是5和2.

如果没有办法从列表中进行迭代和擦除,请告诉我是否有更好的数据结构.我想过使用Vector,但我必须将元素向下移动,如果有很多元素,那将会很昂贵.

#include "roulette.h"
#include <iostream>

uint roulette(uint people, uint step)
{
    std::list<uint>::iterator iterator;
    for(uint i = people; i > 0; i--)
        gl_myList.push_front(i);

    iterator = gl_myList.begin();
    while(people > 1)
    {
        iterator = advanceList(iterator, step - 1);
        uint replaceValue = *iterator; // Node n's value

        auto tempIterator = advanceList(iterator, step);
        uint newValue = *tempIterator; //Node n + step value

        iterator = gl_myList.erase(tempIterator);
        //Makes it past the erase function ONCE.

        //Puts the iterator back to the correct spot, and sets it value
        while(*iterator != replaceValue)
        {
            advanceList(iterator, 1);

        }
        *iterator = newValue;

        people--;
    }

    return *iterator;
}
Run Code Online (Sandbox Code Playgroud)

advanceList

#include "roulette.h"
std::list<uint>::iterator advanceList(std::list<uint>::iterator& start, uint step)
{
    for(uint i = 0; i < step; i++)
    {
        start++;
        if(start == gl_myList.end())
        {
            start = gl_myList.begin();
        }
    }

    return start;
}
Run Code Online (Sandbox Code Playgroud)

Who*_*aig 2

您没有erase()正确使用调用的结果,也没有.end()在下一次迭代之前进行检查。我几乎可以肯定以下是您至少尝试做的事情。请注意,这仍然很脆弱,因为它还没有准备好应对边缘情况(例如初始空列表、0 步长值等):

std::list<uint>::iterator advanceList(std::list<uint>::iterator& start, uint step)
{
    for(uint i = 0; i < step; i++)
    {
        if(++start == gl_myList.end())
            start = gl_myList.begin();
    }

    return start;
}

uint roulette(uint people, uint step)
{
    std::list<uint>::iterator it;
    for(uint i = people; i > 0; i--)
        gl_myList.push_front(i);

    it = gl_myList.begin();
    while (gl_myList.size() > 1)
    {
        it = gl_myList.erase(advanceList(it, step - 1));
        if (it == gl_myList.end())
            it = gl_myList.begin();
    }

    return *it;
}
Run Code Online (Sandbox Code Playgroud)