簡體   English   中英

為什么沒有std :: erase?

[英]Why there is no std::erase?

在閱讀STL時,我意識到沒有提供std::erase 我不確定為什么它不存在。 一個有效的用例如下

std::vector<int> odd { 1, 3, 5, 3, 9, 11, 5, 17 };
std::sort(odd.begin(), odd.end());
std::erase(std::unique(odd.begin(), odd.end()), odd.end());

它嵌入在每個容器中。 如果性能是原因,那么如果對象是連續的,則可以一次刪除它們。 但我想這可以通過幫助模板專業化來實現。

它會如何工作? 它只接受一對迭代器。 迭代器不具備繼續履行其容器的引用(向量的迭代器可以是單純的別名指針)。

那么算法如何修改容器本身呢? 它需要訪問權限。

它必須是成員函數。

2014年底,在圖書館基礎2 TS中添加了統一容器擦除標准/實驗。這最近被投票進入了C ++ - 2a的標准,但即使是github的草案也沒有顯示出來。 我知道gcc,clang和Visual Studio支持實驗。

因此,代替您通常的容器包括以下版本之一:

<experimental/deque>
<experimental/forward_list>
<experimental/list>
<experimental/map>
<experimental/set>
<experimental/string>
<experimental/unordered_map>
<experimental/unordered_set>
<experimental/vector>

這些是來自最近的一篇論文的簽名:

  // <experimental/string>
  template <class charT, class traits, class A, class Predicate>
    void erase_if(basic_string<charT, traits, A>& c, Predicate pred);
  template <class charT, class traits, class A, class U>
    void erase(basic_string<charT, traits, A>& c, const U& value);

  // <experimental/deque>
  template <class T, class A, class Predicate>
    void erase_if(deque<T, A>& c, Predicate pred);
  template <class T, class A, class U>
    void erase(deque<T, A>& c, const U& value);

  // <experimental/vector>
  template <class T, class A, class Predicate>
    void erase_if(vector<T, A>& c, Predicate pred);
  template <class T, class A, class U>
    void erase(vector<T, A>& c, const U& value);

  // <experimental/forward_list>
  template <class T, class A, class Predicate>
    void erase_if(forward_list<T, A>& c, Predicate pred);
  template <class T, class A, class U>
    void erase(forward_list<T, A>& c, const U& value);

  // <experimental/list>
  template <class T, class A, class Predicate>
    void erase_if(list<T, A>& c, Predicate pred);
  template <class T, class A, class U>
    void erase(list<T, A>& c, const U& value);

  // <experimental/map>
  template <class K, class T, class C, class A, class Predicate>
    void erase_if(map<K, T, C, A>& c, Predicate pred);
  template <class K, class T, class C, class A, class Predicate>
    void erase_if(multimap<K, T, C, A>& c, Predicate pred);

  // <experimental/set>
  template <class K, class C, class A, class Predicate>
    void erase_if(set<K, C, A>& c, Predicate pred);
  template <class K, class C, class A, class Predicate>
    void erase_if(multiset<K, C, A>& c, Predicate pred);

  // <experimental/unordered_map>
  template <class K, class T, class H, class P, class A, class Predicate>
    void erase_if(unordered_map<K, T, H, P, A>& c, Predicate pred);
  template <class K, class T, class H, class P, class A, class Predicate>
    void erase_if(unordered_multimap<K, T, H, P, A>& c, Predicate pred);

  // <experimental/unordered_set>
  template <class K, class H, class P, class A, class Predicate>
    void erase_if(unordered_set<K, H, P, A>& c, Predicate pred);
  template <class K, class H, class P, class A, class Predicate>
    void erase_if(unordered_multiset<K, H, P, A>& c, Predicate pred);

序列和算法之間的粘合劑是迭代器(感謝@Pete Becker在這里指出了正確的術語)。 它們歸結為可應用於多個序列(容器)類型的強大算法所需的最小功能。 一個例子是這樣一個片段:

std::vector<int> vec{1, 2, 3, 4};
std::list<int> lst;

std::copy(vec.cbegin(), vec.cend(), std::back_inserter(lst));
std::copy(lst.cbegin(), lst.cend(), std::ostream_iterator<int>(std::cout, " "));

這里, std::copy可以獨立於它所操作的特定序列類型來實現,因為它與迭代器一起工作,這些迭代器用於執行兩項操作: 遍歷序列並提供對其元素的訪問

但是,當從容器中刪除元素時,這具有限制。

在利用( std - )算法時這樣做的必要性足以引起擦除刪除習慣用法是一個眾所周知的模式或范圍庫,它利用整個容器傳遞給算法:

#include <boost/range/algorithm_ext.hpp>

std::vector<int> vec{1, 2, 3, 4};

boost::remove_erase(vec, 3);

最后一個函數調用實際上可以從容器中刪除值為3的元素,因為在該函數調用中沒有隱藏任何信息。 相比之下, *begin / *end (成員)函數的族正是這樣:隱藏抽象背后的信息。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM