总览
C++ 相对于 C 的最大区别就是 C++ 引入了类。而 C++ 的官方就运用类封装了一些模板,称之为“标准模板库” (Standard Template Library)
竞赛常用的标准模板库有:
// 算法库
#include <Algorithm>
// 字符串
#include <string>
// 变长数组
#include <vector>
// 链表
#include <list>
// 队列(普通队列和优先队列)
#include <queue>
// 双端队列
#include <deque>
// 栈
#include <stack>
// 映射
#include <map>
// 二元结构体
#include <pair>
// 集合(有序和无序)
#include <set>
注意:STL 是封装在 std 里的,使用需要引入 std 命名空间。
由于本章涉及的头文件较多,这里统一声明,使用全库且使用 std 命名空间:
#include <bits\stdc++.h>
using namespace std;
Algorithm
Algorithm 总包含很多函数,包括逻辑判断、搜索、复制替换等
1、sort()
Algorithm 里最著名的也许就是 sort() 了,对于 不会写 懒得写排序的人来说绝对是很好的福利。
int a[10] = {9, 2, 4, 2, 6, 8, 3, 5, 0, 7};
main()
{
sort(a, a + 10);
for (int i = 0; i <= 9; ++i)
{
printf("%d ", a[i]);
}
}
sort() 会按照升序进行排列。除此之外,sort() 支持自定义 cmp 函数,该功能可实现降序排序及其他数据结构排序。
typedef struct _struct
{
int a; /* 按照 a 的大小降序排列 */
int b;
} st;
st s[10] = {
{1, 4}, {4, 6}, {3, 43}, {7, 8}, {6, 2}, {2, 7}, {9, 4}, {0, 35}, {8, 21}, {6, 12},
};
bool cmp(st st1, st st2) // cmp 的名称可以自定义,默认最好为 cmp 或 cmp1、cmp2……
{
return st1.a > st2.a;
}
main()
{
sort(s, s + 10, cmp);
for (int i = 0; i <= 9; ++i)
{
printf("(%d, %d) ", s[i].a, s[i].b);
}
}
upper_bound() 和 lower_bound()
lower_bound 返回指向范围中第一个值大于或等于给定值的元素的迭代器
upper_bound 返回指向范围中第一个值大于给定值的元素的迭代器
这个主要可以用于维护单调队列
reverse()
神奇的函数,可以将数组逆序,省下时间。
string str = "0123456789";
main()
{
reverse(str.begin(), str.end());
printf("%s", str.c_str());
}
min()、max()、swap() 等
一些在 < cmath > 里的函数在 Algorithm 里都有重新定义。并且都定义在 std 内,不会产生冲突。
其他函数
本人找到了一篇博文有详细介绍,可以参考:
CSDN-博文链接:C++ algorithm函数简介
string
string 真的是无敌牛* 飞天Plus。至少对于我这种不愿意用 cstring 库,不喜欢 字符数组,不会用 不喜欢 char* 的我(好矫情)来说,它无疑是非大常的好用(说都不会话了)
string str;
main()
{
cin >> str; // 正确,可以使用
// 但 scanf("%s", str); 错误,str 不是 C++ 标准的类型,故无法使用
// 而 string 对于 cin 已经进行了重载,故可以使用
// 以一下写法也是正确的,不过读入的 str.length() 会等于 0,不建议使用
// scanf("%d", str.c_str());
// 通过下标访问字符串中的字符 [范围:0 ~ length() - 1]
for (int i = 0; i < str.length(); ++i)
{
printf("%c ", str[i]);
}
// 输出可以用 printf,但输出整个字符串还需要加上 .c_str()
// 如 printf("%s", str.c_str());
if (str.find('*')) printf("\nchar \'*\' in string\n");
// 同样的函数还有 find_first_of、find_first_not_of
// find_last_of、find_lats_not_of,功能字面理解
// 找到会返回出现满足条件的字符的位置,如果找不到,会返回 string::nops
// 替换
// str.replace(pos, len, str2);
// str.replace(it1, it2, str2);
str.replace(1, 3, "不知道写啥了");
// 等价于 str.replace(str.begin() + 1, str.begin() + 4);
printf("%s\n", str.c_str());
// 子串
// str.substr(pos, len);
str = "123456";
printf("%s\n", str.substr(3, 5).c_str()); // 子串
// 赋值
str.assign("1234"); // 基础的赋值
str.assign(4, '*'); // 等价于 str = "****";
str.assign("1234", 2, 3); // 将 "1234" 的从 2 开始 到 3 的子串赋值给 str
// 相当于 str.assign(string("1234").substr())
// 追加字符串
str.append("-1=33");
printf("%s\n", str.c_str());
// append 的用法和 assign 类似
// str.erase(...) 及 str.insert(...) 的用法类似上面
// string 支持 <、<=、==、!=、>=、>
if (str >= "32") printf("It is larger than \"32\"\n");
// string 函数还具有 compare 函数,其功能相当于运算符,
// compare 成员函数有以下返回值:
// 小于 0 表示当前的字符串小;
// 等于 0 表示两个字符串相等;
// 大于 0 表示另一个字符串小。
if (str.compare("32")) printf("Larger again\n");
// string 有 begin()、end() 两个成员函数返回首尾地址
// 如 sort(str.begin(), str.end());
}
string 也可以使用 流 进行操作,其用 cout 输出原理类似,不多赘述。
vector
Vector 是 C++ 标准模板库中的部分内容,它是一个多功能的,能够操作多种数据结构和算法的模板类和函数库。
定义:
// vector<type> val
vector<int> a; // 一个变长数组
vector<int> b[100]; // 一个维度变长,一个维度定长为 100
vector<vector<double> >c; // 一个二维变长数组
// 注意,定义多维 vector 时,相邻两个 > 号之间要加空格,防止被判定为右移符号 >>
typedef struct _stu{
char name[20];
int age, id;
}stu;
vector<stu> s; // 一个变长结构体数组
访问:
第一种:下标访问,不做赘述
第二种:迭代器(类似指针变量)
// vector<typename>::iterator it;
vector<int> a;
vector<int>::iterator it;
...
main()
{
for (int i = 1; i <= 10; ++i)
{
a.push_back(i);
}
for (int i = 0; i < a.size(); ++i)
{
printf("%d ", a[i]);
}
printf("\n\n");
for (it = a.begin(); it != a.end(); ++it)
{
printf("%d ", *it);
}
}
函数:
函数 | 使用 |
---|---|
末尾添加 push_back(typename t) | v.push_back(41) – O(1) |
删除末尾 pop_back(typename t) | v.pop_back(41) – O(1) |
清空 clear(typename t) | v.clear() – O(n) |
插入 insert(vector< typename >::itearator it, typename t) | v.insert(v.begin() + 2, 41) – O(n) |
删除 erase(vector< typename >::itearator it) | v.erase(v.begin() + 5) – O(n) |
另一种删除使用 erase(vector< typename >::itearator it1, vector< typename >::itearator it2) | v.erase(v.begin() + 5, v.begin() + 7) – O(n) |
(东西较多,未完)
作者:Rotch
日期:2020-10-01
修改:2020-10-04
[2020-10-04]:修正 String 的使用方法
[2020-10-04]:整理 Vector 的使用方法