アルゴリズム競合における C++ STL コンテナー、アルゴリズム、および反復子の詳細な説明

この記事を書く目的の 1 つは、将来いつでも見直すことができるように要約を書くことと、STL とは何か、STL を使用して問題をより効率的かつ怠惰に解決する方法を初心者向けに紹介することです。STL . この記事は久しぶりに更新します. 誰もが監督して一緒に勉強することを歓迎します. 間違いや補足が必要な場合は, コメント欄にメッセージを残してください~ AcWingにジャンプ~

1.STLの考え方

STL ( Standard Template Library、Standard Template Library) は、Hewlett-Packard Labs によって開発された一連のソフトウェアの総称です。現在、主に C++ で使用されている STL は、コンテナー ( Container)、アルゴリズム ( Algorithm)、イテレーター ( Iterator) に大きく分けられます。ほとんどすべての STL コードでテンプレート クラスまたはテンプレート関数が使用されているため、関数とクラスで構成される従来のライブラリよりもコードを再利用できます。

2. STL の 6 つの主要コンポーネント

STL は、相互に組み合わせて使用​​できる 6 つの主要コンポーネントを提供します. これらの 6 つの主要コンポーネントは、コンテナー、アルゴリズム、イテレーター、ファンクター、アダプター、およびスペース コンフィギュレーターです。その中でもコンテナ、アルゴリズム、イテレータはアルゴリズム競技で最も多く使われています

  • コンテナー ( Container): STL コンテナーは、などのさまざまなデータ構造であり、データを格納するために使用されます。実装の観点からは、STL コンテナーは 1 つですvectorstackqueuemapsetclass template
  • Algorithm ( Algorithm): STL のアルゴリズムのほとんどは<algorithm>ヘッダー ファイルで定義されます。ヘッダー ファイルにはsortfindcopyreverseなどの一般的に使用されるさまざまなアルゴリズムが含まれます。実装の観点からは、STL アルゴリズムは 1 つですfunction template
  • 反復子 ( Iterator): STL 反復子は、コンテナーとアルゴリズムの間の接着剤として機能します. 全部で 5 つのタイプがあります. 実装の観点からは、反復子は一種のポインター関連の操作であり、 , などはオーバーロードさopetator*opetator->ますoperator++. class template. すべての STL コンテナーには独自のイテレーターが付属しており、コンテナーの設計者だけが要素をトラバースする方法を知っています。
  • Functor ( Functor): Behavior is similar to function, which can be used as a certain strategy of an algorithm. 実装の観点からは、ファンクターはオーバーoperator()ロードされたclassorですclass template
  • アダプター ( Adaptor): コンテナーまたはファンクターまたはイテレーター インターフェイスを装飾するために使用されるもの。
  • スペース コンフィギュレーター ( Allocator): スペースの構成と管理を担当します。実装の観点から見ると、コンフィギュレーターは、動的なスペース構成、スペース管理、およびスペース解放を実装するツールですclass template

3.STLコンテナ

問題解決の速度を向上させるために、競技会でさまざまなデータ構造やアルゴリズムを使用するふりをするために STL を学ぶ人が多いと思います。実際、STL でコンテナーを使用すると、さまざまなデータ構造を手動で定義する必要がなくなり、STL でアルゴリズムを使用すると、さまざまな基本的なアルゴリズムを手動で実装する必要がなくなるため、この部分はアルゴリズム マスターにとって最も重要な部分であり、次に STL とはコンテナは何ですか?問題でそれらを使用する方法は?

3.1 ベクトル

vector可変長配列とも呼ばれ、<vector>ヘッダー ファイルで定義されます。vectorコンテナは動的スペースです。要素が追加されると、その内部メカニズムが新しい要素を収容するためにスペースを自動的に拡張します。したがって、vectorメモリの使用は、メモリの合理的な使用と使用の柔軟性に大きく役立ちます。

  • vectorと定義されている:
vector<int> v;  // 定义一个vector,其中的元素为int类型
vector<int> v[N];  // 定义一个vector数组,其中有N个vector
vector<int> v(len);  // 定义一个长度为len的vector
vector<int> v(len, x);  // 定义一个长度为len的vector,初始化每个元素为x
vector<int> v2(v1);  // 用v1给v2赋值,v1的类型为vector
vector<int> v2(v1.begin(), v1.begin() + 3);  // 将v1中第0~2三个元素赋值给v2
  • vector一般的に使用される組み込み関数:
// vector中的常用内置函数
vector<int> v = {
    
     1, 2, 3 };  // 初始化vector,v:{1, 2, 3}
vector<int>::iterator it = v.begin();  // 定义vector的迭代器,指向begin()

v.push_back(4);  // 在vector的尾部插入元素4,v:{1, 2, 3, 4}
v.pop_back();  // 删除vector的最后一个元素,v:{1, 2, 3}
// 注意使用lower_bound()与upper_bound()函数时vector必须是有序的,upper_bound()在<algorithm>中
lower_bound(v.begin(), v.end(), 2);  // 返回第一个大于等于2的元素的迭代器v.begin() + 1,若不存在则返回v.end()
upper_bound(v.begin(), v.end(), 2);  // 返回第一个大于2的元素的迭代器v.begin() + 2,若不存在则返回v.end()
v.size();  // 返回vector中元素的个数
v.empty();  // 返回vector是否为空,若为空则返回true否则返回false
v.front();  // 返回vector中的第一个元素
v.back();  // 返回vector中的最后一个元素
v.begin();  // 返回vector第一个元素的迭代器
v.end();  // 返回vector最后一个元素后一个位置的迭代器
v.clear();  // 清空vector
v.erase(v.begin());  // 删除迭代器it所指向的元素,即删除第一个元素
v.erase(v.begin(), v.begin() + 2);  // 删除区间[v.begin(), v.begin() + 2)的所有元素
v.insert(v.begin(), 1);  // 在迭代器it所指向的位置前插入元素1,返回插入元素的迭代器

// 根据下标进行遍历
for (int i = 0; i < v.size(); i++)
	cout << v[i] << ' ';
// 使用迭代器遍历
for (vector<int>::iterator it = v.begin(); it != v.end(); it++)
	cout << *it << ' ';
// for_each遍历(C++11)
for (auto x : v)
	cout << x << ' ';

3.2 スタック

stackstackとも呼ばれ、後入れ先出し(Last In First Out、LIFO) データ構造であり、<stack>ヘッダー ファイルで定義されます。stackコンテナーにより、要素の追加、要素の削除、およびスタックの最上位要素の取得が可能になります。 、ただし、トップを除いて、任意のメソッドでアクセスできるstackその他の要素は。つまり、stackトラバーサル動作は許可されていません

  • stackと定義されている:
stack<int> stk;  // 定义一个stack,其中元素的类型为int
stack<int> stk[N];  // 定义一个stack数组,其中有N个stack
  • stack一般的に使用される組み込み関数:
// stack中的常用内置函数
stack<int> stk;
stk.push(x);  // 在stack中插入元素x
stk.pop();  // 弹出stack的栈顶元素
stk.top();  // 返回stack的栈顶元素
stk.size();  // 返回stack中元素的个数
stk.empty();  // 返回stack是否为空,若为空则返回true否则返回false

3.3弦

stringstringとも呼ばれ、<string>ヘッダー ファイルで定義されます。C スタイルの文字列 (null で終わる文字配列) は複雑すぎて処理できないため、C++ 標準ライブラリではクラスが定義されていますstringデータ構造、メモリ管理などの点で同一ですstringvector<char>ただし、vector<char>単なる「char要素のコンテナ」ではstringなく、単に「char要素のコンテナ」であり、文字列に対するいくつかの操作も拡張します。たとえば、関数stringを使用して C スタイルの文字列に変換できc_str()vector入力はありません。出力ストリーム演算子はオーバーロードされているため、またはそのような操作を直接vector<char>実行することはできませんが、可能であり、文字列のスプライシングを直接実現することはできませんが、はい、演算子はオーバーロードされています.cincoutstringvector<char>stringstring+, +=

  • stringと定義されている:
string str;  // 定义一个空的字符串
string str[N];  // 定义一个string数组,其中有N个string
string str(5, 'a');  // 使用5个字符'a'初始化
string str("abc");  // 使用字符串初始化
  • string一般的に使用される組み込み関数:
// string中的常用内置函数
string str("abcabc");
str.push_back('d');  // 在string尾部插入字符,"abcabcd"
str.pop_back();  // 删除string尾部的字符,"abcabc"
str.length();  // 返回string中字符的个数
str.size();  // 作用与length()相同
str.empty();  // 返回string是否为空,若为空返回true否则返回false
str.substr(1);  // 返回string中从下标为1开始至末尾的子串,"bcabc"
str.substr(0, 2);  // 返回string中从下标为0开始长度为2的子串,"ab"
str.insert(1, 2, 'x');  // 在下标为1的字符前插入2个字符'x',"axxbcabc"
str.insert(1, "yy");  // 在下标为1的字符前插入字符串"yy","ayyxxbcabc"
str.erase(1, 4);  // 删除从位置1开始的4个字符,"abcabc"
str.find('b');  // 返回字符'b'在string中第一次出现的位置,返回1,若不存在则返回-1
str.find('b', 2);  // 返回从位置2开始字符'b'在string中第一次出现的位置,返回4
str.find("bc");  // 同上,返回字符串第一次出现的位置,返回1,若不存在则返回-1
str.find("bc", 2);  // 返回4
str.rfind('b');  // 反向查找,原理同上,返回4,若不存在则返回-1
str.rfind('b', 3);  // 返回1
str.rfind("bc");  // 返回4,若不存在则返回-1
str.rfind("bc", 3);  // 返回1
stoi(str);  // 返回str的整数形式
to_string(value);  // 返回value的字符串形式,value为整型、浮点型等
str[0];  // 用下标访问string中的字符
cout << (str == str) << endl;  // string可比较大小,按字典序
  • stringerase()AND関数の使用法remove():
// string中erase()与remove()的用法
string str1, str2, str3, str4, str5;
str1 = str2 = str3 = str4 = str5 = "I love AcWing! It's very funny!";
str1.erase(15);  // 删除[15,end())的所有元素,"I love AcWing!"
str2.erase(6, 11);  // 从第6个元素(包括)开始往后删除11个元素,"I love's very funny!"
str3.erase(str3.begin() + 2);  // 删除迭代器所指的元素,"I ove AcWing! It's very funny!"
str4.erase(str4.begin() + 7, str4.end() - 11);  // 删除[str4.begin()+7,str4.end()-11)的所有元素,"I love very funny!"
str5.erase(remove(str5.begin(), str5.end(), 'n'), str5.end());  // 删除[str5.begin(),str5.end())中所有字符'n',"I love AcWig! It's very fuy!"

3.4 キュー/priority_queue

queueキューとも呼ばれ、ヘッダー ファイルで定義された先入れ先出し(先入れ先出し、FIFO) のデータ構造です。コンテナーにより、新しい要素を一方の端 (テールと呼ばれる) から追加 (エントリ) できます。キューの)、およびもう一方の端 (キュー ヘッドと呼ばれる) から要素を削除します (デキュー)。<queue>queue

priority_queueプライオリティ キューとも呼ばれ、<queue>ヘッダー ファイルでも定義されます。queue違いは、その中のデータの優先度をカスタマイズできることです。priority_queue基本的な操作を含むすべての機能を備えていますqueueが、これを基に内部ソートが追加されています. その本質はヒープによって実装されているため、小さなルートヒープ大きなルートヒープに分けることができます.小さなルートヒープの小さな要素は並べ替え済み大きなルート ヒープ内の大きな要素が先頭に配置されます。(デフォルトは、作成priority_queue時の大きなルート ヒープです! )

  • queue/priority_queueと定義されている:
queue<int> que;  // 定义一个queue,其中元素的类型为int
queue<int> que[N];  // 定义一个queue数组,其中有N个queue
priority_queue<int> bigHeap;  // 定义一个大根堆
priority_queue<int, vector<int>, greater<int> > smallHeap;  // 定义一个小根堆
  • queue/priority_queue一般的に使用される組み込み関数:
// queue/priority_queue中的常用内置函数
queue<int> que;
priority_queue<int> bigHeap;
que.push(x);  // 在queue的队尾插入元素x
que.pop();  // 出队queue的队头元素
que.front();  // 返回queue的队头元素
que.back();  // 返回queue的队尾元素
que.size();  // 返回queue中元素的个数
que.empty();  // 返回queue是否为空,若为空则返回true否则返回false
bigHeap.top();  // 返回priority_queue的队头元素

3.5と

dequeヘッダー ファイルで定義されたdouble-ended queueとも呼ばれるコンテナーは、一方向の開口部を持つ連続したメモリ空間であり、双方向の開口部を持つ連続した線形空間ですいわゆる双方向開きとは、頭と尻尾の両端にそれぞれ要素を挿入・削除できることを意味し、もちろん頭と尻尾の両端にも要素を挿入できますが、頭が非常に低い。最大の違いは一定の項時間で先頭の要素の挿入と削除ができることであり、2 つ目は分割された空間と連続した空間で動的に構成され、新しいセグメントを作成できるため、容量の概念がないことです。いつでもスペースに追加して、それらをリンクします。<deque>vectordequevectordequevectordequedeque

  • dequeと定義されている:
deque<int> deq;  // 定义一个deque,其中的元素为int类型
deque<int> deq[N];  // 定义一个deque数组,其中有N个deque
deque<int> deq(len);  // 定义一个长度为len的deque
deque<int> deq(len, x);  // 定义一个长度为len的deque,初始化每个元素为x
deque<int> deq2(deq1);  // 用deq1给v2赋值,deq2的类型为deque
deque<int> deq2(deq1.begin(), deq1.begin() + 3);  // 将deq1中第0~2三个元素赋值给deq2
  • deque一般的に使用される組み込み関数:
//deque中的常用内置函数
deque<int> deq = {
    
     1, 2, 3 };  // 初始化vector,v:{1, 2, 3}
deque<int>::iterator it = deq.begin();  // 定义vector的迭代器,指向begin()

deq.push_back(4);  // 在deque的尾部插入元素4,v:{1, 2, 3, 4}
deq.pop_back();  // 删除deque的尾部元素,v:{1, 2, 3}
deq.push_front(4);  // 在deque的头部插入元素4,v:{4, 1, 2, 3}
deq.pop_front();  // 删除deque的头部元素,v:{1, 2, 3}
deq.size();  // 返回deque中元素的个数
deq.empty();  // 返回deque是否为空,若为空则返回true否则返回false
deq.front();  // 返回deque中的第一个元素
deq.back();  // 返回deque中的最后一个元素
deq.begin();  // 返回deque第一个元素的迭代器
deq.end();  // 返回deque最后一个元素后一个位置的迭代器
deq.clear();  // 清空deque
deq.erase(deq.begin());  // 删除迭代器it所指向的元素,即删除第一个元素
deq.erase(deq.begin(), deq.begin() + 2);  // 删除区间[v.begin(), v.begin() + 2)的所有元素
deq.insert(deq.begin(), 1);  // 在迭代器it所指向的位置前插入元素1,返回插入元素的迭代器

// 根据下标进行遍历
for (int i = 0; i < deq.size(); i++)
	cout << deq[i] << ' ';
// 使用迭代器遍历
for (deque<int>::iterator it = deq.begin(); it != deq.end(); it++)
	cout << *it << ' ';
// for_each遍历(C++11)
for (auto x : deq)
	cout << x << ' ';

3.6 マップ/マルチマップ

map/multimapマッピングとも呼ばれ、<map>ヘッダー ファイルで定義され、mapmultimapの基本的な実装メカニズムは赤黒ツリーです。mapの機能は、任意のタイプの要素を別の任意のタイプの要素にマップできるようにすることであり、すべての要素は要素のキー値に従って自動的にソートされます。mapすべての要素は、キー値実際の値pairの両方(つまり、ペア) を持ち、キー値と見なされ実際の値と見なされ2 つの要素が同じキー値を持つことはできません。操作は の操作と似ていますが、唯一の違いはのキー値が繰り返されることです。(key, value)keyvaluemapmultimapmapmultimap

  • map/multimapと定義されている:
map<string, int> mp;  // 定义一个将string映射成int的map
map<string, int> mp[N];  // 定义一个map数组,其中有N个map
multimap<string, int> mulmp;  // 定义一个将string映射成int的multimap
multimap<string, int> mulmp[N];  // 定义一个multimap数组,其中有N个multimap
  • map/multimap一般的に使用される組み込み関数:
// map/multimap中的常用内置函数
map<string, int> mp;
mp["abc"] = 3;  // 将"abc"映射到3
mp["ab"]++;  // 将"ab"所映射的整数++
mp.insert(make_pair("cd", 2));  // 插入元素
mp.insert({
    
     "ef", 5 });  // 同上
mp.size();  // 返回map中元素的个数
mp.empty();  // 返回map是否为空,若为空返回true否则返回false
mp.clear();  // 清空map
mp.erase("ef");  // 清除元素{"ef", 5}
mp["abc"];  // 返回"abc"映射的值
mp.begin();  // 返回map第一个元素的迭代器
mp.end();  // 返回map最后一个元素后一个位置的迭代器
mp.find("ab");  // 返回第一个键值为"ab"的迭代器,若不存在则返回mp.end()
mp.find({
    
     "abc", 3 });  // 返回元素{"abc", 3}的迭代器,若不存在则返回mp.end()
mp.count("abc");  // 返回第一个键值为"abc"的元素数量1,由于map元素不能重复因此count返回值只有0或1
mp.count({
    
     "abc", 2 });  // 返回第一个键值为"abc"的元素数量1,注意和find不一样,count只判断第一个键值
mp.lower_bound("abc");  // 返回第一个键值大于等于"abc"的元素的迭代器,{"abc", 3}
mp.upper_bound("abc");  // 返回第一个键值大于"abc"的元素的迭代器,{"cd", 2}

// 使用迭代器遍历
for (map<string, int>::iterator it = mp.begin(); it != mp.end(); it++)
	cout << (*it).first << ' ' << (*it).second << endl;
// for_each遍历(C++11)
for (auto x : mp)
	cout << x.first << ' ' << x.second << endl;
// 扩展推断范围的for_each遍历(C++17)
for (auto &[k, v] : mp)
	cout << k << ' ' << v << endl;

3.7 セット/マルチセット

set/multisetコレクションとも呼ばれ、<set>ヘッダー ファイルで定義されます。set特徴は、すべての要素が要素のキー値に従って自動的にソートされることです.それsetとは異なり、要素はキー値と実際の値の両方を同時にmap持つことができます. の要素. 要約すると,要素で注文され、繰り返されませんと の特性と使用法はまったく同じです。唯一の違いは、要素の繰り返しが許可されていることと、と の基本的な実装が赤黒ツリーであることです。setsetsetmultisetsetmultisetsetmultiset

  • set/multisetと定義されている:
set<int> st;  // 定义一个set,其中的元素类型为int
set<int> st[N];  // 定义一个set数组,其中有N个set
multiset<int> mulst;  // 定义一个multiset
multiset<int> mulst[N];  // 定义一个multiset数组,其中有N个multiset
  • set/multiset一般的に使用される組み込み関数:
// set/multiset中的常用内置函数
set<int> st;
st.insert(5);  // 插入元素5
st.insert(6);  // 同上
st.insert(7);  // 同上
st.size();  // 返回set中元素的个数
st.empty();  // 返回set是否为空,若为空返回true否则返回false
st.erase(6);  // 清除元素6
st.begin();  // 返回set第一个元素的迭代器
st.end();  // 返回set最后一个元素后一个位置的迭代器
st.clear();  // 清空set
st.find(5);  // 返回元素5的迭代器,若不存在则返回st.end()
st.count(5);  // 返回元素5的个数1,由于set元素不会重复,因此count返回值只有0或1
st.lower_bound(5);  // 返回第一个键值大于等于5的元素的迭代器,返回元素5的迭代器
st.upper_bound(5);  // 返回第一个键值大于5的元素的迭代器,返回元素7的迭代器

// 使用迭代器遍历
for (set<int>::iterator it = st.begin(); it != st.end(); it++)
	cout << (*it) << ' ';
// for_each遍历(C++11)
for (auto x : st)
	cout << x << ' ';

3.8 unordered_map/unordered_set

unordered_map/unordered_setそれらはそれぞれヘッダーファイルで定義され<unordered_map>テーブル構造が<unordered_set>内部的に使用されており、クイック検索機能を備えています。最大の違いhash、 の要素が順不同であり、追加、削除、変更、およびチェックの時間の複雑さがO ( 1 ) O(1)であることです。map/setunordered_map/unordered_setO ( 1 ) (map/set追加、削除、変更、チェックの時間計算量はO ( logn ) O(logn)O ( log n ) )ですが関数はサポートされていませんlower_bound()/upper_bound()

  • unordered_map/unordered_setと定義されている:
unordered_set<int> st;  // 定义一个unordered_set,其中的元素类型为int
unordered_set<int> st[N];  // 定义一个unordered_set数组,其中有N个unordered_set
unordered_map<int, int> mp;  // 定义一个unordered_map
unordered_map<int, int> mp[N];  // 定义一个unordered_map数组,其中有N个unordered_map
  • unordered_map/unordered_set一般的に使用される組み込み関数:
// unordered_map/unordered_set中的常用内置函数
unordered_set<int> st;
unordered_map<int, int> mp;
st.insert(5);  // 插入元素5
st.insert(6);  // 同上
st.insert(7);  // 同上
st.size();  // 返回unordered_set中元素的个数
st.empty();  // 返回unordered_set是否为空,若为空返回true否则返回false
st.erase(6);  // 清除元素6
st.find(5);  // 返回元素5的迭代器,若不存在则返回st.end()
st.count(5);  // 返回元素5的个数,由于unordered_set元素不会重复,因此count返回值只有0或1
st.begin();  // 返回unordered_set第一个元素的迭代器
st.end();  // 返回unordered_set最后一个元素后一个位置的迭代器
st.clear();  // 清空unordered_set
mp.insert(make_pair(1, 2));  // 插入元素{1, 2}
mp.insert({
    
     3, 4 });  // 同上
mp.size();  // 返回unordered_map中元素的个数
mp.empty();  // 返回unordered_map是否为空,若为空返回true否则返回false
mp.erase(3);  // 清除元素{3, 4}
mp.find(1);  // 返回第一个键值为1的迭代器,若不存在则返回mp.end()
mp.count(1);  // 返回第一个键值为1的元素数量,由于unordered_map元素不能重复因此count返回值只有0或1
mp.begin();  // 返回unordered_map第一个元素的迭代器
mp.end();  // 返回unordered_map最后一个元素后一个位置的迭代器
mp.clear();  // 清空unordered_map

// 使用迭代器遍历
for (unordered_set<int>::iterator it = st.begin(); it != st.end(); it++)
	cout << (*it) << ' ';
// for_each遍历(C++11)
for (auto x : st)
	cout << x << ' ';

// 使用迭代器遍历
for (unordered_map<int, int>::iterator it = mp.begin(); it != mp.end(); it++)
	cout << (*it).first << ' ' << (*it).second << endl;
// for_each遍历(C++11)
for (auto x : mp)
	cout << x.first << ' ' << x.second << endl;
// 扩展推断范围的for_each遍历(C++17)
for (auto &[k, v] : mp)
	cout << k << ' ' << v << endl;

4.STLアルゴリズム

C++ 標準ライブラリは、汎用アルゴリズムのセットを定義します. 汎用アルゴリズムと呼ばれる理由は、標準ライブラリの型だけでなく、組み込みの配列型やその他の型のシーケンスに対しても、さまざまなコンテナーを操作できることを意味します. . . 汎用アルゴリズムは<algorithm>ヘッダー ファイルで定義され、標準ライブラリは、ヘッダー ファイルで定義される一連の一般化算術アルゴリズム(Generalized Numeric Algorithm)も定義します。<numeric>使用方法は次のとおりです。

#include <iostream>
#include <algorithm>
#include <numeric>
using namespace std;

int main()
{
    
    
	// 使用STL容器时将数组指针改为迭代器即可

	int a[5] = {
    
     1, 2, 3, 4, 5 };
	int b[5] = {
    
     0 };

	// 排序算法
	sort(a, a + 5);  // 将区间[0, 5)内元素按字典序从小到大排序
	sort(a, a + 5, greater<int>());  // 将区间[0, 5)内元素按字典序从大到小排序
	reverse(a, a + 5);  // 将区间[0, 5)内元素翻转
	nth_element(a, a + 3, a + 5);  // 将区间[0, 5)中第a + 3个数归位,即将第3大的元素放到正确的位置上,该元素前后的元素不一定有序

	// 查找与统计算法
	find(a, a + 5, 3);  // 在区间[0, 5)内查找等于3的元素,返回迭代器,若不存在则返回end()
	binary_search(a, a + 5, 2);  // 二分查找区间[0, 5)内是否存在元素2,若存在返回true否则返回false
	count(a, a + 5, 3);  // 返回区间[0, 5)内元素3的个数

	// 可变序列算法
	copy(a, a + 2, a + 3);  // 将区间[0, 2)的元素复制到以a+3开始的区间,即[3, 5)
	replace(a, a + 5, 3, 4);  // 将区间[0, 5)内等于3的元素替换为4
	fill(a, a + 5, 1);  // 将1写入区间[0, 5)中(初始化数组函数)
	unique(a, a + 5);  // 将相邻元素间的重复元素全部移动至末端,返回去重之后数组最后一个元素之后的地址
	remove(a, a + 5, 3);  // 将区间[0, 5)中的元素3移至末端,返回新数组最后一个元素之后的地址

	// 排列算法
	next_permutation(a, a + 5);  // 产生下一个排列{ 1, 2, 3, 5, 4 }
	prev_permutation(a, a + 5);  // 产生上一个排列{ 1, 2, 3, 4, 5 }

	// 前缀和算法
	partial_sum(a, a + 5, b);  // 计算数组a在区间[0, 5)内的前缀和并将结果保存至数组b中,b = { 1, 3, 6, 10, 15 }

	// 差分算法(感谢willem248同学的补充)
	adjacent_difference(a, a + 5, b);  // 计算数组a区间[0, 5)内的差分并将结果保存至数组b中,b = { 1, 1, 1, 1, 1 }
	adjacent_difference(a, a + 5, b, plus<int>());  // 计算相邻两元素的和,b = { 1, 3, 5, 7, 9 }
	adjacent_difference(a, a + 5, b, multiplies<int>());  // 计算相邻两元素的乘积,b = { 1, 2, 6, 12, 20 }

	return 0;
}

おすすめ

転載: blog.csdn.net/m0_51755720/article/details/120616163