Um dos propósitos de escrever este artigo é escrever um resumo para que você possa revisá-lo a qualquer momento no futuro e apresentar o que é STL e como usar STL para resolver problemas de forma mais eficiente e preguiçosa para aqueles que são novos no assunto. STL . Este artigo será atualizado por um longo tempo. Todos são bem-vindos para supervisionar e estudar juntos. Se houver erros ou precisar ser complementado, deixe uma mensagem na área de comentários ~ Ir para AcWing ~
CONTEÚDO
1. Conceito STL
STL ( Standard Template Library
, Standard Template Library), é um nome coletivo para uma série de softwares desenvolvidos pela Hewlett-Packard Labs. Agora aparecendo principalmente em C++, o STL é amplamente dividido em: contêiner ( Container
), algoritmo ( Algorithm
) e iterador ( Iterator
). Quase todo código STL usa classes de modelo ou funções de modelo , o que oferece melhores oportunidades de reutilização de código do que as bibliotecas tradicionais compostas de funções e classes.
2. Seis componentes principais do STL
STL fornece seis componentes principais, que podem ser usados em combinação uns com os outros.Esses seis componentes principais são contêineres, algoritmos, iteradores, functores, adaptadores e configuradores de espaço. Dentre eles, containers, algoritmos e iteradores são os mais utilizados em competições de algoritmos .
- Container (
Container
): os contêineres STL são várias estruturas de dados , comovector
,stack
,queue
, etc., usados para armazenar dados. Do ponto de vista da implementação, os contêineres STL são um só .map
set
class template
- Algoritmo (
Algorithm
): A maioria dos algoritmos de STL são definidos no<algorithm>
arquivo de cabeçalho, que inclui vários algoritmos comumente usados, comosort
,find
,copy
,reverse
etc. Do ponto de vista da implementação, o algoritmo STL é umfunction template
. - Iterator ( ): O iterador STL atua como a cola entre o contêiner e o algoritmo .
Iterator
Existem cinco tipos no total. Do ponto de vista da implementação, o iterador é um tipo de operações relacionadas a ponteiros, comoopetator*
, e etc. . Todos os contêineres STL vêm com seus próprios iteradores e apenas o designer do contêiner sabe como percorrer seus elementos.opetator->
operator++
class template
- Functor (
Functor
): O comportamento é semelhante a uma função, que pode ser usada como uma determinada estratégia de um algoritmo.Do ponto de vista da implementação, um functor éoperator()
umclass
ouclass template
. - Adaptador (
Adaptor
): Uma coisa usada para decorar um container ou functor ou interface de iterador. - Configurador de espaços (
Allocator
): Responsável pela configuração e gestão dos espaços. Do ponto de vista da implementação, o configurador é uma ferramenta que implementa configuração de espaço dinâmico, gerenciamento de espaço e liberação de espaçoclass template
.
3. Recipiente STL
Acredito que muitas pessoas aprendem STL para melhor fingir usar várias estruturas de dados e algoritmos na competição para melhorar a velocidade de resolução de problemas. De fato, usar contêineres em STL não exige que você defina várias estruturas de dados manualmente, e usar algoritmos em STL não exige que você implemente vários algoritmos básicos manualmente; são os recipientes?Como usá-los no problema?
3.1 vetor
vector
Também conhecido como array de comprimento variável , é definido no <vector>
arquivo de cabeçalho. vector
O container é um espaço dinâmico . À medida que os elementos são adicionados, seu mecanismo interno automaticamente expande o espaço para acomodar novos elementos. Portanto, vector
o uso da memória é de grande ajuda para o uso racional da memória e a flexibilidade de uso.
vector
é definido como:
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
Funções integradas comumente usadas para:
// 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 pilha
stack
Também conhecida como pilha , é uma estrutura de dados last-in-first-out (Last In First Out, LIFO), definida no <stack>
arquivo de cabeçalho, stack
o contêiner permite adicionar elementos, remover elementos e obter o elemento do topo da pilha , mas exceto pelo topo, não há stack
outros elementos que , ou seja, stack
nenhum comportamento de travessia é permitido .
stack
é definido como:
stack<int> stk; // 定义一个stack,其中元素的类型为int
stack<int> stk[N]; // 定义一个stack数组,其中有N个stack
stack
Funções integradas comumente usadas para:
// 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 cordas
string
Também conhecido como string , definido <string>
no arquivo de cabeçalho. Strings estilo C (arrays de caracteres terminados em nulo) são muito complicados de lidar, então a biblioteca padrão C++ define uma string
classe. string
e vector<char>
são idênticos em termos de estruturas de dados, gerenciamento de memória, etc. No entanto, vector<char>
é simplesmente um " char
contêiner de elementos", string
não apenas um " char
contêiner de elementos", ele também estende algumas operações em strings, por exemplo, funções string
podem ser usadas c_str()
para converter strings no estilo C e vector
não há entrada o operador de fluxo de saída está sobrecarregado, portanto não é possível vector<char>
executar diretamente cin
ou cout
tais operações, mas string
é possível, e vector<char>
a emenda de strings não pode ser realizada diretamente, mas string
sim, o operador string
está sobrecarregado .+, +=
string
é definido como:
string str; // 定义一个空的字符串
string str[N]; // 定义一个string数组,其中有N个string
string str(5, 'a'); // 使用5个字符'a'初始化
string str("abc"); // 使用字符串初始化
string
Funções integradas comumente usadas para:
// 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可比较大小,按字典序
string
O uso da funçãoerase()
ANDremove()
:
// 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 fila/prioridade_fila
queue
Também conhecida como fila , é uma estrutura de dados do tipo primeiro a entrar, primeiro a sair<queue>
(First In First Out, FIFO) definida no arquivo de cabeçalho. queue
O contêiner permite que novos elementos sejam adicionados (entrada) de uma extremidade (chamada cauda da fila ) e do outro lado (chamado de cabeçalho da fila ) para remover elementos (dequeue).
priority_queue
Também conhecida como fila de prioridade , ela também é definida no <queue>
arquivo de cabeçalho, queue
a diferença é que podemos customizar a prioridade dos dados nela contidos. priority_queue
Ele tem todos os recursos , incluindo queue
operações básicas, mas uma classificação interna é adicionada nessa base . classificados Na frente, os elementos maiores na grande pilha raiz vêm primeiro. ( O padrão é o grande heap raiz quando criado! )priority_queue
queue/priority_queue
é definido como:
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
Funções integradas comumente usadas para:
// 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 e
deque
Também conhecido como double-ended queue , definido <deque>
no arquivo de cabeçalho, vector
o container é um espaço de memória contínuo com abertura unidirecional, deque
e é um espaço linear contínuo com abertura bidirecional . A chamada abertura bidirecional significa que os elementos podem ser inseridos e excluídos em ambas as extremidades da cabeça e da cauda, respectivamente. Claro, os elementos vector
também podem ser inseridos em ambas as extremidades da cabeça e da cauda, mas a eficiência da inserção no cabeça está muito baixa. deque
A vector
maior diferença é que deque
permite a inserção e exclusão de elementos na cabeça utilizando tempo de termo constante, e a segunda é que deque
não há conceito de capacidade, pois é composto dinamicamente por espaços segmentados e contínuos, podendo um novo segmento ser adicionados a qualquer espaço de tempo e vinculá-los.
deque
é definido como:
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
Funções integradas comumente usadas para:
//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 mapa/multimapa
map/multimap
Também conhecido como mapeamento , é definido no <map>
arquivo de cabeçalho map
e multimap
o mecanismo de implementação subjacente de e é uma árvore rubro-negra. map
A função de é ser capaz de mapear qualquer tipo de elemento para outro tipo arbitrário de elemento , e todos os elementos serão classificados automaticamente de acordo com o valor da chave do elemento. map
Todos os elementos são pair
, tendo valores chave e reais (ou seja, pares), são considerados valores chave , são considerados valores reais , e dois elementos não podem ter o mesmo valor chave. A operação é semelhante à de , a única diferença é que o valor da chave de pode ser repetido.(key, value)
key
value
map
multimap
map
multimap
map/multimap
é definido como:
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
Funções integradas comumente usadas para:
// 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 conjunto/multiconjunto
set/multiset
Também conhecido como coleção , é definido no <set>
arquivo de cabeçalho. set
A característica é que todos os elementos serão classificados automaticamente de acordo com o valor-chave do elemento. set
Ao contrário map
disso, os elementos podem ter set
valores-chave e valores reais ao mesmo tempo set
. Os elementos de . Então, em resumo, set
os elementos in são ordenados e não repetidos . multiset
As características e o uso de e set
são exatamente os mesmos, a única diferença é que multiset
elementos repetidos são permitidos set
e multiset
a implementação subjacente de e é uma árvore rubro-negra.
set/multiset
é definido como:
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
Funções integradas comumente usadas para:
// 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
Eles são respectivamente definidos no arquivo de cabeçalho <unordered_map>
e a estrutura da tabela <unordered_set>
é utilizada internamente , que tem a função de recuperação rápida. hash
Comparado com map/set
a maior diferença unordered_map/unordered_set
é que os elementos são desordenados e a complexidade de tempo para adicionar, excluir, modificar e verificar é O (1) O(1)O ( 1 ) (map/set
a complexidade de tempo de adicionar, excluir, modificar e verificar éO (logn) O(logn)O ( log n ) ) , mas não suportalower_bound()/upper_bound()
funções.
unordered_map/unordered_set
é definido como:
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
Funções integradas comumente usadas para:
// 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. Algoritmo STL
A biblioteca padrão C++ define um conjunto de algoritmos genéricos . A razão pela qual eles são chamados de genéricos significa que eles podem operar em uma variedade de contêineres, não apenas em tipos de biblioteca padrão, mas também em tipos de matriz integrados e até mesmo em outros tipos de sequências . _ O algoritmo genérico é definido <algorithm>
no arquivo de cabeçalho, e a biblioteca padrão também define um conjunto de algoritmos aritméticos generalizados (algoritmo numérico generalizado), que são definidos no <numeric>
arquivo de cabeçalho. O modo de uso é o seguinte:
#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;
}