这里有你想要的STL

这篇文章是写算法的时候关于C++数据结构通过自己+各篇其余文章得来,以做记录

vector

动态数组

vector<int> v(10) //初始化了10个默认值为0的元素
vector<int> v(10,1)//  初始化了10个值为1的元素
vector<vector<int> > v(10, vector<int>(8, 1))// 10行8列全部为1
int m = v.size()//获取行
int n = v[0].size()// 获取列

vector<char> v11({ 'O','X','X','O','X' });
vector<vector<char>> vx({ {'O','X','O','O','O','X'} ,
                        { 'O','O','X','X','X','O'},
                       {'X','X','X','X','X','O'},
                       {'O','O','O','O','X','X'},
                        {'X','X','O','O','X','O'} ,
                        {'O','O','X','X','X','X'} });
vector<int> v;
v.assign(10,0);
vector<vector<int> > v1;
v.assign(10,vector(10,1));

pair

pair是将2个数据组合成一组数据,当需要这样的需求时就可以使用pair,如

  1. stl中的map就是将key和value放在一起来保存。另一个应用是,当一个函数需要返回2个数据的时候,可以选择pair。
  2. pair的实现是一个结构体,主要的两个成员变量是first second 因为是使用struct不是class,所以可以直接使用pair的成员变量。

其标准库类型–pair类型定义在#include 头文件中
初始化和操作

pair<T1, T2> p1;            //创建一个空的pair对象(使用默认构造),它的两个元素分别是T1和T2类型,采用值初始化。
p1.first;                   // 返回对象p1中名为first的公有数据成员
p1.second;                 // 返回对象p1中名为second的公有数据成员

生成

pair<T1, T2> p1(v1, v2);    //创建一个pair对象,它的两个元素分别是T1和T2类型,其中first成员初始化为v1,second成员初始化为v2。
make_pair(v1, v2);          // 以v1和v2的值创建一个新的pair对象,其元素类型分别是v1和v2的类型。

比较

p1 < p2;                    // 两个pair对象间的小于运算,其定义遵循字典次序:如 p1.first < p2.first 或者 !(p2.first < p1.first) && (p1.second < p2.second) 则返回true。
p1 == p2;                  // 如果两个对象的first和second依次相等,则这两个对象相等;该运算使用元素的==操作符。

都是一样的make_pair()显得更加方便无需写出型别, 就可以生成一个pair对象

map

map是STL的一个关联容器,它提供一对一的hash。

第一个可以称为关键字(key),每个关键字只能在map中出现一次;
第二个可能称为该关键字的值(value);


map<string,vector<string>> m //string 到 vector< string >映射
//插入 即当map中有这个关键字时,insert操作是不能在插入数据的,但是用数组方式就不同了,它可以覆盖以前该关键字对 应的值
m.insert(pair<string, vector<string>>("777",vector<string>())
m["123"]=vector<string>()
m["123"].push_back("hhh")
m["123"].push_back("xxx")
m["123"]="aaa"
//删除
m.erase("123")
// 使用find()方法对集合进行检索,如果找到查找的的键值,则返回该键值的迭代器位置;否则,返回集合最后一个元素后面的一个位置,即end()

m.find("666")!=m.end()

//使用count,返回的是被查找元素的个数。如果有,返回1;否则,返回0。注意,map中不存在相同元素,所以返回值只能是1或0。
m.count("666")!=0


find和count

相比起来count写法更简洁

map 与 unordered_map

map: 内部实现了一个红黑树(红黑树是非严格平衡二叉搜索树,而AVL是严格平衡二叉搜索树),红黑树具有自动排序的功能,因此map内部的所有元素都是有序的,红黑树的每一个节点都代表着map的一个元素。因此,对于map进行的查找,删除,添加等一系列的操作都相当于是对红黑树进行的操作。map中的元素是按照二叉搜索树(又名二叉查找树、二叉排序树,特点就是左子树上所有节点的键值都小于根节点的键值,右子树所有节点的键值都大于根节点的键值)存储的,使用中序遍历可将键值按照从小到大遍历出来。

unordered_map: 内部实现了一个哈希表(也叫散列表,通过把关键码值映射到Hash表中一个位置来访问记录,查找的时间复杂度可达到O(1),其在海量数据处理中有着广泛应用)。因此,其元素的排列顺序是无序的。哈希表详细介绍

#include <iostream>  
#include <unordered_map>  
#include <map>
#include <string>  
using namespace std;
int main()
{
 
    map<int, string> map = { { 1, "一" },{ 3, "三" },{2,"二"},{4,"四"} }; 
    auto iter = map.begin();
    while (iter != map.end())
    {
        cout << iter->first << "," << iter->second << endl;
        ++iter;
    }
    cout << endl;
    unordered_map<int, string> unmap = { { 1, "一" },{ 3, "三" },{2,"二"},{4,"四"} };
   
    auto uniter = unmap.begin();
    while (uniter != unmap.end())
    {
        cout << uniter->first << "," << uniter->second << endl;
        ++uniter;
    }
}

在这里插入图片描述

set 集合

实现了红黑树(Red-Black Tree)的平衡二叉检索树的数据结构,在插入元素时,它会自动调整二叉树的排列,把该元素放到适当的位置,以确保每个子树根节点的键值大于左子树所有节点的键值,而小于右子树所有节点的键值;另外,还得确保根节点的左子树的高度与有字数的高度相等,
这样,二叉树的高度最小,从而检索速度最快。要注意的是,它不会重复插入相同键值的元素,而采取忽略处理。

set<string> visit
visit.insert("666")
visit.erase("666")
// 使用find()方法对集合进行检索,如果找到查找的的键值,则返回该键值的迭代器位置;否则,返回集合最后一个元素后面的一个位置,即end()。
visit.find("666") 
visit.find("666")!=visit.end()




set与unordered_set区别和map与unordered_map区别类似:

set基于红黑树实现,红黑树具有自动排序的功能,因此map内部所有的数据,在任何时候,都是有序的。
unordered_set基于哈希表,数据插入和查找的时间复杂度很低,几乎是常数时间,而代价是消耗比较多的内存,无自动排序功能。底层实现上,使用一个下标范围比较大的数组来存储元素,形成很多的桶,利用hash函数对key进行映射到不同区域进行保存

priority_queue 优先队列

既然是队列那么先要包含头文件#include , 他和queue不同的就在于我们可以自定义其中数据的优先级, 让优先级高的排在队列前面,优先出队

//升序队列
priority_queue <int,vector<int>,greater<int> > q;
//降序队列
priority_queue <int,vector<int>,less<int> >q;

其他操作与其他一致

string

string x="Hello_World";
    /*默认截取从0到npos.重载原型为string substr(_off=0,_count=npos);npos一般表示为string类中不存在的位置,_off表示字符串的开始位置,_count截取的字符的数目*/
    cout<<x.substr()<<endl;
    cout<<x.substr(5)<<endl;//截取x[5]到结尾,即npos.重载原型为string substr(_off,_count=npos)
    cout<<x.substr(0,5)<<endl;//以x[0]为始,向后截取5位(包含x[0]),重载原型string substr(_off,_count)


find 没有规定两边,只有开始的pos查找后续所有

发布了178 篇原创文章 · 获赞 140 · 访问量 2万+

猜你喜欢

转载自blog.csdn.net/qq_42146775/article/details/104318980