用C ++循环跳过矢量元素?

时间:2018-09-13 23:58:15

标签: c++ for-loop

我的任务是创建一个'x'数字向量,并使用“ Eratosthenes筛”在该向量中找到质数。我遍历向量,将所有非素元素替换为零。然后,我做了一个for循环来擦除所有零。循环删除了大多数零,但跳过了一些

vector<int> primes;
int userNum = 0; //variable for user to input the size of the vector
cout << "Enter your num, brah";
cin >> userNum;
for (int i = 2; i < userNum; i++) //creates a vector of numbers
{
    primes.push_back(i);
}


int j = 0; //variable to find non-primes

for (int p = primes[0]; p < primes.size(); p++) //loop to replace non-primes with zeros
{
    j = p+p;

    while (j < (primes.size() +2)) {



        replace(primes.begin(), primes.end(), j, 0);

        j+= p;

    }
}

for (int y = 0; y < primes.size(); y++) { //loop to erase the zeros from the vector
    cout << "y1 " << primes[y] << " ";   //cout simply just to find see what is going on
    if (primes[y] == 0) {
        primes.erase(primes.begin() +y);
        cout << "y2: " << y << endl;  //cout simply just to find see what is going on
    }

}

cout << "New Vector is: " << endl; //loop to print the vector
for (int l = 0; l < primes.size(); l++)
{

    cout << primes[l] << ", ";
}

我得到的输出是: 新的向量是: 2,3,5,7,0,11,13,0,17,19,0,23,0,0,29,31,0,0,37,0,41,43,0,47,0, 0、53、0、0、59、61、0、0、67、0、71、73、0、0、79、0、83、0、0、89、0、0、0、97、0,程序以退出代码结束:0

2 个答案:

答案 0 :(得分:4)

无需编写循环来从向量中删除元素。使用erase-remove idiom

primes.erase(std::remove(primes.begin(), primes.end(), 0), primes.end());

上面的方法使用std::remove将不需要擦除的元素移动到向量的“左侧”或正面,并返回指向要删除的第一个元素的迭代器右侧”。然后primes.erase()实际上是通过从对std::remove的调用返回的迭代器开始的操作,从向量中删除要删除的元素。

如果不确定语句的工作方式,可以将语句分为两行:

// returns an iterator to where the elements to erase are to be removed
auto iter = std::remove(primes.begin(), primes.end(), 0);

// Now actually erase them, starting at iter
primes.erase(iter, primes.end());

答案 1 :(得分:1)

可以肯定的一个问题是,您将跳过元素,因为当您从序列中删除某些内容时,其后的所有内容的索引都会降低1。

我在这里做了一个简化的删除代码版本,只是试图从向量中删除每个元素:

string vecToStr(const vector<int> &foos) {
  std::stringstream result;
  std::copy(foos.begin(), foos.end(), std::ostream_iterator<int>(result, " "));
  return result.str();
}

int main() {
  vector<int> foos = { 0,1,2,3,4,5,6 };
  for (int y = 0; y < foos.size(); y++) { //loop to erase the zeros from the vector
    foos.erase(foos.begin() + y);
    cout << "foos is now: " << vecToStr(foos) << " y is " << y << "\n";
  }
  cout << "foos is now: " << vecToStr(foos) << "\n";
  char c;
  cin >> c;
}

以下是输出:

foos is now: 1 2 3 4 5 6  y is 0
foos is now: 1 3 4 5 6  y is 1
foos is now: 1 3 5 6  y is 2
foos is now: 1 3 5  y is 3
foos is now: 1 3 5

您可以看到如何删除第0个元素,然后将值1的元素移入索引0,但是y然后变为1,因此将其跳过,然后在索引1处删除2,将3移入索引2。等

对此有多种方法(请参见Remove elements of a vector inside the loop),老式的C语言实现方法是从头开始:

  int y = foos.size();
  while(y--) {
    foos.erase(foos.begin() + y);
    cout << "foos is now: " << vecToStr(foos) << " y is " << y << "\n";
  }