Estaba mirando la documentación de la API para stl vector, y noté que no había ningún método en la clase de vector que permitiera la eliminación de un elemento con un cierto valor. Esto parece una operación común, y parece extraño que no haya una forma integrada de hacer esto.
145
Respuestas:
std::remove
en realidad no borra el elemento del contenedor, pero devuelve el nuevo iterador final al que se puede pasarcontainer_type::erase
para hacer la eliminación REAL de los elementos adicionales que ahora están al final del contenedor:fuente
vec.end()
garantiza que sea el mismo en ambos lados de la llamadastd::remove
? Me parece que leer otras partes de la web es seguro, pero debe indicarse claramente.vec.end()
no necesita ser el mismo; solo necesita ser correcto (que es).vec.end()
necesita ser lo mismo, pero está bien porquestd::remove
no lo cambia. Si lo cambiara (e invalidara el valor anterior), entonces habría un problema: el orden de evaluación de los parámetros no está especificado y, por lo tanto, no sabría si el segundovec.end()
todavía es válido en el momento en que se usa. La razón por la que es igual es simple,std::remove
no cambia el tamaño del contenedor, solo mueve el contenido.std::remove
solo un argumento; eso esconst char *_Filename
. ¿Qué método necesito llamar?remove
que elimina un archivo. Debe incluir<algorithm>
para acceder a la versión deremove
que trata con contenedores.Si desea eliminar un elemento, lo siguiente será un poco más eficiente.
o puede evitar los gastos generales de mover los artículos si el pedido no le importa:
fuente
Use el método global std :: remove con el iterador de inicio y fin, y luego use std :: vector.erase para eliminar realmente los elementos.
Enlaces de documentación
std :: remove http://www.cppreference.com/cppalgorithm/remove.html
std :: vector.erase http://www.cppreference.com/cppvector/erase.html
Gracias a Jim Buck por señalar mi error.
fuente
Las otras respuestas cubren cómo hacerlo bien, pero pensé que también señalaría que no es realmente extraño que esto no esté en la API de vectores: es ineficiente, la búsqueda lineal a través del vector para el valor, seguido de un montón de copiar para eliminarlo.
Si está haciendo esta operación intensivamente, puede valer la pena considerar std :: set en su lugar por este motivo.
fuente
Si tiene un vector sin clasificar, simplemente puede intercambiar con el último elemento del vector y luego
resize()
.Con un recipiente ordenada, podrás mejor con
std::vector::erase()
. Tenga en cuenta que hay unstd::remove()
definido en<algorithm>
, pero que en realidad no hace el borrado. (Lea la documentación detenidamente).fuente
Una solución más corta (que no te obliga a repetir el nombre del vector 4 veces) sería usar Boost:
Ver http://www.boost.org/doc/libs/1_64_0/libs/range/doc/html/range/reference/algorithms/new/remove_erase.html
fuente
De c ++ 20 :
Se introdujo una función no miembro
std::erase
, que toma el vector y el valor para eliminarlos como entradas.ex:
fuente
map::erase
!Vea también std :: remove_if para poder usar un predicado ...
Aquí está el ejemplo del enlace de arriba:
fuente
Si quieres hacerlo sin ningún extra incluye:
fuente
Hay dos formas en que puede usar para borrar un elemento en particular. tomemos un vector
1) Forma no eficiente: aunque parece ser bastante eficiente, no es porque la función de borrado elimina los elementos y desplaza todos los elementos hacia la izquierda en 1. por lo que su complejidad será O (n ^ 2)
2) Manera eficiente (RECOMENDADO) : También se conoce como ERASE - REMOVE idioms .
La salida del algoritmo de eliminación es:
como tipo de retorno de eliminar es iterador al nuevo final de ese rango.
Ahora use la función de borrado del vector para eliminar elementos del nuevo extremo al extremo anterior del vector. Requiere O (1) tiempo.
entonces este método funciona en O (n)
fuente
* *
* *
C ++ 20 proporciona una manera fácil de hacerlo ahora. Se pone tan simple como:
Deberías consultar std :: erase y std :: erase_if .
No solo eliminará todos los elementos del valor (aquí '0'), lo hará en O (n) complejidad de tiempo. Que es lo mejor que puedes conseguir.
Si su compilador no es compatible con C ++ 20, debe usar el lenguaje erase-remove :
fuente