Как удалить каждый кратный 2 элемент в векторе по индексу - PullRequest
0 голосов
/ 25 июня 2019

Я пытаюсь удалить каждый 2-й элемент из целочисленного вектора в C ++

int n = 10001;    
std::vector<int> sieve;    

for (int i = 2; i <= n; ++i)
    sieve.push_back(i);


for (int i = 2; i < sieve.size(); i += 2)
    sieve.erase(sieve.begin() + i);

Я хочу удалить каждый 2-й элемент из вектора (который будет кратен 2 в диапазоне от 2 до 10001),Вывод таков:

// index, value
0 2
1 3
2 5
3 6
4 8
5 9
6 11
7 12
8 14
9 15
10 17
....

Таким образом, удаляются 4, 10 и 16, как и ожидалось.Однако все еще есть многократные 2, то есть 6, 8, 12, 14

РЕДАКТИРОВАТЬ Решено с помощью метода @Retired Ninja, размещенного в комментариях.(Сделать это в обратном порядке)

for (int i = 2; i <= n; i++)
    sieve.push_back(i);

for (int i = sieve.size(); i >= p; i -= p)
    sieve.erase(sieve.end() - i);

Ответы [ 2 ]

2 голосов
/ 25 июня 2019

Когда вы стираете второй элемент, итератор следующего элемента уменьшается на 1. Таким образом, увеличение 1 переменной цикла в порядке.

int n = 100;    
std::vector<int> sieve;    

for (int i = 2; i <= n; ++i)
    sieve.push_back(i);


for (int i = 2; i < sieve.size(); i += 1)
    sieve.erase(sieve.begin() + i);

И еще один способ в случае стирания pth элемента:

    int cnt=0;
    int l=sieve.size();
    for (int i = 2; i < l; i += p){
        sieve.erase(sieve.begin() + (i-cnt));
            cnt++;
    }
0 голосов
/ 25 июня 2019

Как насчет этого? Это удаляет каждый элемент nth, начинающийся с start с vec.

Он выполняется на месте, включает только изменение размера одного массива, и каждый не стираемый элемент перемещается ровно один раз.

void remove(std::size_t nth, std::size_t start, std::vector<int> &vec)
{
    std::size_t step;
    for (step = 1; start < vec.size(); ++step, start += nth)
    {
        for (std::size_t i = 1; i < nth && start + i < vec.size(); ++i)
        {
            vec[start + i - step] = vec[start + i];
        }
    }
    vec.resize(vec.size() - (step - 1));
}
...