0%

STL库常用API汇总

汇总了c++ STL 库中常用的API用法

常用API

vector

1
2
3
4
5
6
vector<int> a;
a.resize(N); // 扩容
reverse(a.begin(), a.end()); //倒序
swap(a[0], a[1]); //交换位置0 和 1的元素
a.assign(b.begin(), b.end()); // b 拷贝到 a
a.erase(a.begin()+1); //删除第一个元素

sort

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
struct Node{
Node(int idx_, int w_, int p1_, int p2_){
idx = idx_; w = w_; p1 = p1_; p2 = p2_;
}
static bool cmp(){

}
bool operator <(const Node& data){ // 升序排列
return w < data.w;
}
int idx;
int w;
int p1;
int p2;
};

vector<Node> test;
sort(test.begin(), test.end()); //结构体中重载 < 符号 来对自定义的 vector升序排序,要实现逆序排列 可以重载

string

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
string a = "123";
string b = a.substr(0,1); //第一个参数代表起始位置,第二个为长度 提取子串
string a = string(5,'0'); //初始化长度为5的全0填充的字符串 "00000"
a.at(0); //访问0位置的字符
a.resize(N); //和vector一样的扩容方法
a.erase(10, 4) //从位置=10的字符开始 删除4个;不带第二个参数 表示删到结尾
a.insert(14,6,'*') //向 位置14前面 插入 6 个 "*"
a.find("b",5) //从下标5开始查找 字符串“b”出现的位置 用if(pos == string::npos) 用来判断是否找到子串。

a.erase(0,a.find_first_not_of(" ")); //去掉字符串左右两端的空格
a.erase(a.find_last_not_of(" ") + 1);
/// 用 stringstream 分割 指定字符 分开的 字符串
stringstream ss(a);
string item;
while(ss >> item) cout << item << endl; //获取 字符串中的单词 按空格分割
while (std::getline(ss, item, '_')){
cout << item << endl;
}

1
2
3
4
5
6
7
8
9
10
11
12
13
14
// 将 字符串按照 特定字符分割   “11*11+12”
vector<int> split_string(string& s){
vector<int> re;
int p1 = 0, p2 = 0;
for(; p2 < s.size(); p2++){
if(s[p2] == '+' || s[p2] == '-' || s[p2] == '*'){
re.push_back(stoi(s.substr(p1, p2-p1)));
re.push_back(s[p2]);
p1 = p2+1;
}
}
re.push_back(stoi(s.substr(p1, p2-p1)));
return re;
}

stringstream用法

头文件 include<sstream>

字符串分割函数

1
2
3
4
5
6
7
8
void split(const string s, vector<string>& vs, const char delim= ' '){
istringstream iss(s);
string temp;
while (getline(iss,temp,delim)){
vs.emplace_back(move(temp));
}
if (!s.empty() && s.back() == delim) vs.push_back({});//加这句的原因是getline不会识别最后一个delim,避免误判"172.16.254.1.","2001:0db8:85a3:0:0:8A2E:0370:7334:"之类的情况
}

Hash

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
unordered_map<string, int>  dict; // 声明unordered_map对象

// 插入数据的三种方式
dict.insert(pair<string,int>("apple",2));
dict.insert(unordered_map<string, int>::value_type("orange",3));
dict["banana"] = 6;
// 判断是否有元素
if(dict.empty())
cout<<"该字典无元素"<<endl;
else
cout<<"该字典共有"<<dict.size()<<"个元素"<<endl;
// 遍历
unordered_map<string, int>::iterator iter;
for(iter=dict.begin();iter!=dict.end();iter++)
cout<<iter->first<<ends<<iter->second<<endl;
// 删除
dict.erase('a');

queue

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
/*队列*/
queue<int> a;

/*优先队列*/
priority_queue<int, vector<int>, std::less<int> > maxHeap; // 大顶堆 堆顶的元素最大
priority_queue<int, vector<int>, std::greater<int> > minHeap; // 小顶堆 堆顶元素最小
//greater和less是std实现的两个仿函数(就是使一个类的使用看上去像一个函数。其实现就是类中实现一个operator(),这个类就有了类似函数的行为,就是一个仿函数类了)
int a = maxHeap.top(); //获取堆顶最大元素
maxHeap.pop(); //弹出堆顶元素
maxHeap.push(); //向堆中增加元素 堆顶元素永远最大


/*双端队列*/
deque<int> a; // 双端队列 结合了栈和队列的性质,既可以从头部插入 也可以从尾部插入
deque<int> b(a); // 定义并用双端队列a初始化双端队列b
deque<int> a(&n[1], &n[4]); // 将n[1]、n[2]、n[3]作为双端队列a的初值
deq.size();
deq.resize();
deq.push_front(const T& x); // 头部添加元素
deq.push_back(const T& x); //尾部添加元素
deq.insert(iterator it, const T& x); //任意位置插入一个元素
deq.pop_front(); // 头部删除元素
deq.pop_back(); //末尾删除元素
deq.front(); //访问第一个元素
deq.back(); //访问最后一个元素

优先队列 priority_queue

头文件#include <queue>, 可以自定义其中数据的优先级, 让优先级高的排在队列前面,优先出队。本质是通过大小顶堆这种数据结构实现。

定义

priority_queue<Type, Container, Functional>

Type 就是数据类型,Container 就是容器类型(Container必须是用数组实现的容器,比如vector,deque等等,但不能用 list。STL里面默认用的是vector),Functional 就是比较的方式,当需要用自定义的数据类型时才需要传入这三个参数,使用基本数据类型时,只需要传入数据类型,默认是大顶堆

基本操作:

  • top 访问队头元素
  • empty 队列是否为空
  • size 返回队列内元素个数
  • push 插入元素到队尾 (并排序)
  • emplace 原地构造一个元素并插入队列
  • pop 弹出队头元素
  • swap 交换内容

自定义类型用法