Namespaces
Variants

std:: remove, std:: remove_if

From cppreference.net
Algorithm library
Constrained algorithms and algorithms on ranges (C++20)
Constrained algorithms, e.g. ranges::copy , ranges::sort , ...
Execution policies (C++17)
Non-modifying sequence operations
Batch operations
(C++17)
Search operations
Modifying sequence operations
Copy operations
(C++11)
(C++11)
Swap operations
Transformation operations
Generation operations
Removing operations
remove remove_if
Order-changing operations
(until C++17) (C++11)
(C++20) (C++20)
Sampling operations
(C++17)

Sorting and related operations
Partitioning operations
Sorting operations
Binary search operations
(on partitioned ranges)
Set operations (on sorted ranges)
Merge operations (on sorted ranges)
Heap operations
Minimum/maximum operations
Lexicographical comparison operations
Permutation operations
C library
Numeric operations
Operations on uninitialized memory
Défini dans l'en-tête <algorithm>
(1)
template < class ForwardIt, class T >
ForwardIt remove ( ForwardIt first, ForwardIt last, const T & value ) ;
(constexpr depuis C++20)
(jusqu'à C++26)
template < class ForwardIt, class T = typename std:: iterator_traits

< ForwardIt > :: value_type >
constexpr ForwardIt remove ( ForwardIt first, ForwardIt last,

const T & value ) ;
(depuis C++26)
(2)
template < class ExecutionPolicy, class ForwardIt, class T >

ForwardIt remove ( ExecutionPolicy && policy,

ForwardIt first, ForwardIt last, const T & value ) ;
(depuis C++17)
(jusqu'à C++26)
template < class ExecutionPolicy, class ForwardIt,

class T = typename std:: iterator_traits
< ForwardIt > :: value_type >
ForwardIt remove ( ExecutionPolicy && policy,

ForwardIt first, ForwardIt last, const T & value ) ;
(depuis C++26)
template < class ForwardIt, class UnaryPred >
ForwardIt remove_if ( ForwardIt first, ForwardIt last, UnaryPred p ) ;
(3) (constexpr depuis C++20)
template < class ExecutionPolicy, class ForwardIt, class UnaryPred >

ForwardIt remove_if ( ExecutionPolicy && policy,

ForwardIt first, ForwardIt last, UnaryPred p ) ;
(4) (depuis C++17)

Supprime tous les éléments satisfaisant des critères spécifiques de la plage [ first , last ) et retourne un itérateur pointant après le nouveau dernier élément de la plage.

1) Supprime tous les éléments qui sont égaux à value (en utilisant operator == ).
3) Supprime tous les éléments pour lesquels le prédicat p renvoie true .
2,4) Identique à (1,3) , mais exécuté selon la policy .
Ces surcharges participent à la résolution de surcharge seulement si toutes les conditions suivantes sont satisfaites :

std:: is_execution_policy_v < std:: decay_t < ExecutionPolicy >> est true .

(jusqu'à C++20)

std:: is_execution_policy_v < std:: remove_cvref_t < ExecutionPolicy >> est true .

(depuis C++20)


Si le type de valeur de ForwardIt n'est pas CopyAssignable , le comportement est indéfini.

(jusqu'à C++11)

Si le type de * first n'est pas MoveAssignable , le comportement est indéfini.

(depuis C++11)

Table des matières

Explication

La suppression s'effectue en décalant les éléments de la plage de telle manière que les éléments à ne pas supprimer apparaissent au début de la plage.

  • Le décalage est effectué par copy assignment (until C++11) move assignment (since C++11) .
  • L'opération de suppression est stable : l'ordre relatif des éléments non supprimés reste inchangé.
  • La séquence sous-jacente de [ first , last ) n'est pas raccourcie par l'opération de suppression. En prenant result comme itérateur retourné :
  • Chaque élément de [ result , last ) a un état valide mais non spécifié, car l'affectation par déplacement peut éliminer des éléments en déplaçant à partir d'éléments qui étaient initialement dans cette plage.
(depuis C++11)

Paramètres

first, last - la paire d'itérateurs définissant l'intervalle des éléments à traiter
value - la valeur des éléments à supprimer
policy - la politique d'exécution à utiliser
p - prédicat unaire qui retourne ​ true si l'élément doit être supprimé.

L'expression p ( v ) doit être convertible en bool pour chaque argument v de type (éventuellement const) VT , où VT est le type de valeur de ForwardIt , indépendamment de la catégorie de valeur , et ne doit pas modifier v . Ainsi, un type de paramètre VT & n'est pas autorisé , pas plus que VT sauf si pour VT un déplacement est équivalent à une copie (depuis C++11) . ​

Exigences de type
-
ForwardIt doit satisfaire aux exigences de LegacyForwardIterator .
-
UnaryPredicate doit satisfaire aux exigences de Predicate .

Valeur de retour

Itérateur après la fin pour la nouvelle plage de valeurs (si ce n'est pas end , alors il pointe vers une valeur non spécifiée, et il en va de même pour les itérateurs vers toutes les valeurs entre cet itérateur et end ).

Complexité

Étant donné N comme std:: distance ( first, last ) :

1,2) Exactement N comparaisons en utilisant operator == .
3,4) Exactement N applications du prédicat p .

Exceptions

Les surcharges avec un paramètre de modèle nommé ExecutionPolicy signalent les erreurs comme suit :

  • Si l'exécution d'une fonction invoquée dans le cadre de l'algorithme lève une exception et que ExecutionPolicy fait partie des politiques standard , std::terminate est appelé. Pour tout autre ExecutionPolicy , le comportement est défini par l'implémentation.
  • Si l'algorithme ne parvient pas à allouer de la mémoire, std::bad_alloc est levée.

Implémentation possible

remove (1)
template<class ForwardIt, class T = typename std::iterator_traits<ForwardIt>::value_type>
ForwardIt remove(ForwardIt first, ForwardIt last, const T& value)
{
    first = std::find(first, last, value);
    if (first != last)
        for (ForwardIt i = first; ++i != last;)
            if (!(*i == value))
                *first++ = std::move(*i);
    return first;
}
remove_if (3)
template<class ForwardIt, class UnaryPred>
ForwardIt remove_if(ForwardIt first, ForwardIt last, UnaryPred p)
{
    first = std::find_if(first, last, p);
    if (first != last)
        for (ForwardIt i = first; ++i != last;)
            if (!p(*i))
                *first++ = std::move(*i);
    return first;
}

Notes

Un appel à remove est généralement suivi d'un appel à la fonction membre erase d'un conteneur pour supprimer effectivement les éléments du conteneur. Ces deux invocations ensemble constituent ce qu'on appelle l'idiome erase-remove .

Le même effet peut également être obtenu par les fonctions non-membres suivantes :

(depuis C++20)

Les fonctions membres de conteneur portant des noms similaires member functions list::remove , list::remove_if , forward_list::remove , et forward_list::remove_if suppriment les éléments retirés.

Ces algorithmes ne peuvent pas être utilisés avec des conteneurs associatifs tels que std::set et std::map car leurs types d'itérateurs ne déréférencent pas vers des types MoveAssignable (les clés dans ces conteneurs ne sont pas modifiables).

La bibliothèque standard définit également une surcharge de std::remove dans <cstdio> , qui prend un const char * et est utilisée pour supprimer des fichiers.

Parce que std::remove prend la value par référence, il peut avoir un comportement inattendu s'il s'agit d'une référence à un élément de la plage [ first , last ) .

Macro de test de fonctionnalité Valeur Std Fonctionnalité
__cpp_lib_algorithm_default_value_type 202403 (C++26) Initialisation par liste pour les algorithmes ( 1,2 )

Exemple

Le code suivant supprime tous les espaces d'une chaîne en décalant tous les caractères non-espace vers la gauche puis en effaçant l'excédent. Ceci est un exemple de erase-remove idiom .

#include <algorithm>
#include <cassert>
#include <cctype>
#include <complex>
#include <iomanip>
#include <iostream>
#include <string>
#include <string_view>
#include <vector>
int main()
{
    std::string str1{"Quick  Red  Dog"};
    std::cout << "1) " << std::quoted(str1) << '\n';
    const auto noSpaceEnd = std::remove(str1.begin(), str1.end(), ' ');
    std::cout << "2) " << std::quoted(str1) << '\n';
    // Les espaces sont supprimés de la chaîne uniquement logiquement.
    // Notez que nous utilisons une vue, la chaîne originale n'est toujours pas réduite :
    std::cout << "3) " << std::quoted(std::string_view(str1.begin(), noSpaceEnd))
              << ", taille : " << str1.size() << '\n';
    str1.erase(noSpaceEnd, str1.end());
    // Les espaces sont supprimés physiquement de la chaîne.
    std::cout << "4) " << std::quoted(str1) << ", taille : " << str1.size() << '\n';
    std::string str2 = "Jumped\n Over\tA\vLazy \t  Fox\r\n";
    str2.erase(std::remove_if(str2.begin(), 
                              str2.end(),
                              [](unsigned char x) { return std::isspace(x); }),
               str2.end());
    std::cout << "5) " << std::quoted(str2) << '\n';
    std::vector<std::complex<double>> nums{{2, 2}, {1, 3}, {4, 8}};
    #ifdef __cpp_lib_algorithm_default_value_type
        nums.erase(std::remove(nums.begin(), nums.end(), {1, 3}), nums.end());
    #else
        nums.erase(std::remove(nums.begin(), nums.end(), std::complex<double>{1, 3}),
                   nums.end());
    #endif
    assert((nums == std::vector<std::complex<double>>{{2, 2}, {4, 8}}));
}

Sortie :

1) "Quick  Red  Dog"
2) "QuickRedDog Dog"
3) "QuickRedDog", size: 15
4) "QuickRedDog", size: 11
5) "JumpedOverALazyFox"

Rapports de défauts

Les rapports de défauts modifiant le comportement suivants ont été appliqués rétroactivement aux normes C++ précédemment publiées.

DR S'applique à Comportement publié Comportement corrigé
LWG 283 C++98 T devait être EqualityComparable , mais
le type de valeur de ForwardIt n'est pas toujours T
exige que le type de valeur de ForwardIt
soit CopyAssignable à la place

Voir aussi

copie une plage d'éléments en omettant ceux qui satisfont des critères spécifiques
(modèle de fonction)
supprime les éléments en double consécutifs dans une plage
(modèle de fonction)
supprime les éléments satisfaisant des critères spécifiques
(objet fonction algorithme)