为什么std :: remove没有删除数组的最后一个元素

Me *_*d I 1 c++

可能重复:
STL删除无法按预期工作?

对不起,我是C++ 11和迭代器的新手.这应该删除数组中的所有数字3,但它不会删除最后一个.为什么?

#include <algorithm>
#include <array>
#include <iostream>

int main() {

   std::array<int, 8> a{{9, 3, 4, 5, 33, 5, 6, 3}};

   int N(3);

   std::remove(a.begin(), a.end(), N);

   for (int i : a) {
      std::cout << i << '\n';
   }

}
Run Code Online (Sandbox Code Playgroud)

我得到输出:

{ 9, 4, 5, 33, 5, 6, 6, 3 }
                        ^
                        |
             // the last 3 is still there
Run Code Online (Sandbox Code Playgroud)

K-b*_*llo 6

std::remove在迭代器上运行; 因此,它无法从容器中实际擦除元素.这就是为什么它通常与erase以下一起使用:

a.erase(std::remove(a.begin(), a.end(), N), a.end());
Run Code Online (Sandbox Code Playgroud)

正如其他人所说,这不适用array.


chr*_*ris 6

算法不了解底层容器.它们只是根据给定的迭代器进行迭代,并独立于容纳它们的容器访问元素.这就是为什么有一种称为擦除删除的习惯用法,它采用以下模式:

container.erase(std::remove(it1, it2, value), std::end(container));
Run Code Online (Sandbox Code Playgroud)

std::remove将保留的元素移动到前面(感谢K-ballo)并将迭代器返回到未移动元素的开头.然后,erase擦除从那一点到结束的所有内容.

由于std::array封装了固定大小的数组,我将使您的示例适应std::vector:

std::vector<int> v{9, 3, 4, 5, 33, 5, 6, 3};
v.erase(std::remove(std::begin(v), std::end(v), 3), std::end(v));
Run Code Online (Sandbox Code Playgroud)

唯一的其他东西要注意的是较为普遍的形式.begin().end(),这在内置阵列工作也是如此.这包含在C++ 11中.

  • `remove`不会将移除的元素移动到后面,它会将keept元素移动到前面.后面的元素具有未指定的值. (2认同)