D2.5库函数STL

1.#include<algorithm>

sort排序

在C++中自带的排序函数,对数组中任意连续切片进行排序。
头文件#include<algorithm>
例如有数组A[1000]

  • 对数组从A[a]到A[b-1]进行升序排序:sort(A+a,A+b)
  • 对数组从A[a]到A[b-1]进行降序排序:sort(A+a,A+b,greater<int>())
    其中,greater<int>()表示降序排序数据类型为int的元素
#include<iostream>
#include<algorithm>
using namespace std;

const int N = 1e6+10;
int a[N];
int main()
{
    for(int i = 0; i < 10; i++)  cin >> a[i];
    
    sort(a+1,a+9);
    for(int i = 0; i < 10; i++)  cout << a[i] << " ";
    cout << endl;
    
    sort(a+1,a+9,greater<int>());
    for(int i = 0; i < 10; i++)  cout << a[i] << " ";
    cout << endl;
    return 0;
}

在这里插入图片描述

swap()函数

swap 参数是引用的,不需要取地址。

	int num[4] = {0,1,2,3};
    swap(num[0],num[3]);

reverse()函数

反转一个可迭代对象的元素顺序,比如数组。
使用reverse(num+a,num+b);可以反转切片

    int num[4] = {0,1,2,3};
    reverse(num,num+4);

max() & min()

使用max(a,b) & min(a,b)
甚至还可以max({1,2,3,4})?里面是一个数组的形式…

写在中间

  1. 大多数标准容器都提供 .swap() 成员函数,一般用于交换两个容器的内容;
  2. 对于清空容器,某些容器没有成员函数 .clear(),可以使用直接赋值为空的方法:
stack<int> S1 = stack<int>();
set<double> Set1 = set<double>();

2.#include<vector>动态数组相关

  • 开局:
#include<vector>
using namespace std;
int main()
{...}

开数组

  • 定义:vector<数据类型> name
    数据类型可以是int\float\double…vector<int> a就定义了一个储存整数的动态数组a,不用设置大小。

访问元素

直接访问a[1]…

在末尾插入元素

使用 数组名.push_back(新元素);

#include <vector>
using namespace std;

vector<int> a;//[]
int main()
{
	a.push_back(1);//[1]
	a.push_back(2);//[1,2]
	...
	return 0;
}

获取长度

使用 数组名.size()

#include <vector>
using namespace std;

vector<int> a;
int main()
{
	...
	for(int i = 0; i < a.size(); i ++)
		cout << a[i];
	return 0;
}

修改元素

直接修改a[1] = 9; ... a[1] = 3;

从末尾删除元素

使用 数组名.pop_back();
因为从内部某处删除元素还得涉及到元素的整体移动。

清空所有元素

无需一个一个.pop_back(),使用 数组名.clear()

判断vector是否为空

使用 数组名.empty(),返回一个bool值,true为空。

改变数组的长度

使用 数组名.resize(修改后的长度,初值);
若是改长数组,初值是赋给多出来的部分;如果不写初值新多出来的长度默认为0;
如果是改短,之间删除原有的,变为空;

访问尾下标

使用 数组名,back()

使用库<algorithm>的sort函数进行排序

  • 对于vector<int> 是对大小进行升序排序
  • 对于vector<string>是对字符串进行字典序的升序排序

动态数组储存自定义数据

除了储存基本数据类型,还可以储存自定义的数据类型,比如结构体。

#include<iostream>
#include <vector>
#include<string>
using namespace std;

struct Student
{
    int age;
    string name;
    int Class;
};
vector<Student> a;

int main()
{
    Student s1,s2;
    s1.age = 19;
    s1.name = "xiaoguang";
    s1.Class = 2;
    s2.age = 18;
    s2.name = "xiaohong";
    s2.Class = 1;
    
    a.push_back(s1);
    a.push_back(s2);
    
    cout << a.size();
    return 0;
}

构造函数快速创建动态数组

使用vector<int> num(长度,初始值);
直接初始化一个已经具有长度且全部都是初始值的动态数组。
括号中具有两个参数,如果省略初始值,那么初始值默认为0;如果同时省略长度和初始值,那么num是空的,不可访问。

int n = 10;
vector<int> nums1(n,6);
//开了一个已经有10个元素6的动态数组。

vector<int> nums2;

动态二维数组

使用vector<vector<int> > 数组名。可以理解为开辟的数组里面放的是数组。动态二维数组可以是不等长的。

  • 快速构建
    vector<vector<int> > num(行数,vector<int>(列数,0))
    包含行数、列数、初值
#include<iostream>
#include<vector>
using namespace std;

vector<vector<int>> vec1(2,vector<int>(3,0)) 

大小还是可以再变的,只不过一开始初始化就有下面:
在这里插入图片描述

  • 比如vector<vector<int>> A(N); 定义了一个二维数组,一共有N行,每行的列数是动态变化的

  • 矩阵:

#include<iostream>
#include<vector>
using namespace std;

vector<vector<int> > num;
vector<int> num1;
vector<int> num2;
int main()
{
    num1.push_back(1);
    num1.push_back(2);
    num2.push_back(3);
    num2.push_back(4);
    
    num.push_back(num1);
    num.push_back(num2);
    
    for(int i = 0; i < num.size(); i ++)
    {
        for(int j = 0; j < num[i].size(); j++)
        {
            cout << num[i][j] << " ";
        }
        cout << endl;
    }
    return 0;
        
}

输出为2x2的矩阵:

1 2
3 4

3.#include<set>集合

开局:

#include<set>
using namespace std;

创建集合

使用set<数据类型> 集合名
储存相同数据类型的数据,初始化成功之后集合是空的,注意集合中元素不可以重复

set<int> s1;
set<string> s23;

插入元素

使用 集合名.insert(要插入的元素);
在集合末尾插入一个新的元素,如果要插入的元素在集合已经存在,那么将不会执行任何操作(也不会报错)。

删除元素

使用 集合名.erase(要删除的元素);

判断元素是否存在

使用 集合名.count(要判断的元素)
这是一个表达式,如果存在返回1,不存在返回0.

遍历集合

使用set<数据类型>::iterator it;定义一个迭代器。定义迭代器可以直接使用auto it;
注意集合名.begin()返回容器中起始元素的迭代器,集合名.end()函数返回容器的尾后迭代器。
注意遍历set是从小到大进行遍历的,也就是自动排好序了。

set<int> set1 = {"a","b","c"};
for set<int>::iterator it = set1.begin(); it != set1.end(); it ++)
{
	cout << *it << endl;
}
  • 这里可以把set<int>::iterator看做一种数据类型,就像for(int i = 0;...)
  • 输出的时候要解引用 *it
  • 尽管添加元素到集合的时候是无序的,但是遍历元素的时候打印出来的集合元素师有序排列的。int、float类数据按照大小进行排序;char、string类数据则按照字典序进行排序,即从第一个字符开始,逐个字符比较两个字符串的 ASCII 值

清空集合

使用 集合名.clear();会清空结合中的元素,同时释放掉set占用的内存。

代码示例:

#include<iostream>
#include<set>
#include<string>
using namespace std;

int main()
{
     set<string> S1 = {"China","USA","England"};
     S1.insert("US");
     S1.erase("China");
     if(S1.count("China"))
     {
         cout << "China is in the set."<<endl;
     }
     for(set<string>::iterator it = S1.begin(); it != S1.end(); it ++)
     {
         cout << *it << " ";
    }
    cout << endl;
    return 0;
}
输出为:England US USA 

4.#include<map>映射

映射是指两个集合之间的相互对应关系。
在这里插入图片描述

类似python中的字典,一个key只能对应一个value,不同的key的value可以相同。
映射的关键字是map,在map中是以pair<>的方式储存的

创建映射

使用map<key,value> 映射名;.其中key和value都是某种数据结构,如map<name,class> Class1;。初始建立的map是空映射。

添加键值pair

  • 使用 map名.insert(键值pair);
  • 键值pair有两种方法建立:1.make_pair(key,value)该表达式返回一对键值pair;
    一般使用2.直接添加 映射名[key] = value;
  • 如果要插入的key已经存在,那么插入无效。

访问映射的key

  • 访问的方式和数组一样,使用[],如 dict["Tom"];如果map中不存在访问的该key,那么就会自动创建该key并且设置默认初值。
  • 修改也是直接进行修改:dict["Tom"] = 4;

判断key是否存在

使用表达式 映射名.count(key),如果存在返回1;否则返回0.

遍历映射

  • 使用map<key,value>::iterator it;定义一个迭代器。
  • 定义迭代器可以直接使用auto it;编译器自动判断。
  • 这里迭代器指向的元素是一对键值pair,有firstsecond两个成员变量,分别代表keyvalue
  • 打印的时候还是使用解引用(*it).first或者(*it).second等价于it->first或者it->secnd
for(map<string,int>::iterator it = dict,begin(); it != dict.end(); it++)
{
	cout << it->first << "->" it->second << " ";
}

获取键值pair个数

使用 映射名.size()

清空map数据

使用 映射名.clear();清空数据同时释放map占用的内存

更多应用

除了基本数据,使用map还可以map套mapmap套set

map<int,set<string> > M1;
map<int,map<string,int> > M2;

代码示例

#include<iostream>
#include<map>
#include<string>
using namespace std;

int main()
{
    map<string,int> Class;
    
    int num = Class.size();
    cout << "There are " << num << "pair:" << endl;
    for(map<string,int>::iterator it = Class.begin(); it != Class.end(); it++)
    {
        cout << it->first << "->" << it->second << " ";
    }
    cout << endl;
    
    Class.insert(make_pair("张飞",1));
    Class["小航"] = 3;
    
    num = Class.size();
    cout << "There are " << num << "pair:" << endl;
    for(map<string,int>::iterator it = Class.begin(); it != Class.end(); it++)
    {
        cout << it->first << "->" << it->second << " ";
    }
    
    return 0;
}
//输出:
There are 0pair:

There are 2pair:
小航->3 张飞->1 

5.#include<stack>

定义

使用stack<数据类型> 栈名;

进栈和出栈

使用栈名.push(新元素)入栈
栈名.pop()出栈并且返回栈顶元素

访问栈顶元素

使用栈名.top()返回栈顶元素

查看大小

使用栈名.size()返回大小

判空

使用栈名.empty()表达式返回bool值
注意<stack>容器没有.clear()成员函数!!

完全可以使用vector来代替stack,vector更加灵活

6.#include<queue>队列

定义

使用queue<数据类型> 队列名;

进队和出队

使用队名.push(新元素)入队
队名.pop()出对并且返回队首元素

访问队首队尾

使用队名.front() 队名.back()

查看大小

使用队名.size()返回大小

判空

使用队名.empty()表达式返回bool值
注意<stack>容器没有.clear()成员函数!!

6.C++11标准auto关键字

  1. 以下三种写法是等效的:
	//1
	for(map<string,int>::iterator it = M1.begin(); it != M1.end(); it++)
	{
	    cout << it->first << "->" << it->second << " ";
	}
	
	//2
	for(auto it = M1.begin(); it != M1.end(); it++)
	{
	    cout << it->first << "->" << it->second << " ";
	}
	
	//3
	for(auto &pair : M1)
	{
	    cout << pair.first << "->" << pair.second << " ";
	}

前两种it->first其实和(*it).first是等效的;第三种是引用的用法。

7.#include<string>字符串

定义

使用string 字符串名(长度,初值);
例如string name(4,'K');

修改

整体修改,直接重新赋值即可name = "Marry";
细节修改,name[1] = 'u';

运算符

+:连接字符串
=:赋值
==:判断俩个字符串是否相同

#include<string> 
#include<iostream> 
using namespace std;

int main()
{
	string s;
	cin >> s;
	cout <<s << endl;
} 

成员函数

使用 .size()函数获取字符串的长度

  • 12
    点赞
  • 14
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值