算法训练之STL使用汇总

vector

vector常用函数

#include<vector>
vector<int> a,b;
//b为向量,将b的0-2个元素赋值给向量a
a.assign(b.begin(),b.begin()+3);
//a含有4个值为2的元素
a.assign(4,2);
//返回a的最后一个元素
a.back();
//返回a的第一个元素
a.front();
//返回a的第i元素,当且仅当a存在
a[i];
//清空a中的元素
a.clear();
//判断a是否为空,空则返回true,非空则返回false
a.empty();
//删除a向量的最后一个元素
a.pop_back();
//删除a中第一个(从第0个算起)到第二个元素,也就是说删除的元素从a.begin()+1算起(包括它)一直到a.begin()+3(不包括它)结束
a.erase(a.begin()+1,a.begin()+3);
//在a的最后一个向量后插入一个元素,其值为5
a.push_back(5);
//在a的第一个元素(从第0个算起)位置插入数值5,
a.insert(a.begin()+1,5);
//在a的第一个元素(从第0个算起)位置插入3个数,其值都为5
a.insert(a.begin()+1,3,5);
//b为数组,在a的第一个元素(从第0个元素算起)的位置插入b的第三个元素到第5个元素(不包括b+6)
a.insert(a.begin()+1,b+3,b+6);
//返回a中元素的个数
a.size();
//返回a在内存中总共可以容纳的元素个数
a.capacity();
//将a的现有元素个数调整至10个,多则删,少则补,其值随机
a.resize(10);
//将a的现有元素个数调整至10个,多则删,少则补,其值为2
a.resize(10,2);
//将a的容量扩充至100,
a.reserve(100);
//b为向量,将a中的元素和b中的元素整体交换
a.swap(b);
//b为向量,向量的比较操作还有 != >= > <= <
a==b;

vector 创建二维数组

创建

vector<vector<int>>ans;
//不过这个时候ans 大小是0,不能访问。

初始化

// 创建有n行
vector<vector<int>>ans(N);
//n*m,并初始化为0
vector<vector<int>>ans(N,vector<int>(m,0));

例子

int main()
{
   while(cin>>n>>q){
       vector<vector<int>>ans(N);
       while(q--){
           cin>>fg;
           if(fg == 0){
               cin>>t>>x;
               ans[t].push_back(x);
           }else if(fg == 1){
               cin>>t;
               show(ans[t]);
           }else{
               cin>>t;
               ans[t].clear();
           }
       }
   }
    return 0;
}

list

list常用函数

Lst1.assign() 给list赋值
Lst1.back() 返回最后一个元素
Lst1.begin() 返回指向第一个元素的迭代器
Lst1.clear() 删除所有元素
Lst1.empty() 如果list是空的则返回true
Lst1.end() 返回末尾的迭代器
Lst1.erase() 删除一个元素
Lst1.front() 返回第一个元素
Lst1.get_allocator() 返回list的配置器
Lst1.insert() 插入一个元素到list中
Lst1.max_size() 返回list能容纳的最大元素数量
Lst1.merge() 合并两个list
Lst1.pop_back() 删除最后一个元素
Lst1.pop_front() 删除第一个元素
Lst1.push_back() 在list的末尾添加一个元素
Lst1.push_front() 在list的头部添加一个元素
Lst1.rbegin() 返回指向第一个元素的逆向迭代器
Lst1.remove() 从list删除元素
Lst1.remove_if() 按指定条件删除元素
Lst1.rend() 指向list末尾的逆向迭代器
Lst1.resize() 改变list的大小
Lst1.reverse() 把list的元素倒转
Lst1.size() 返回list中的元素个数
Lst1.sort() 给list排序
Lst1.splice() 合并两个list
Lst1.swap() 交换两个list
Lst1.unique() 删除list中重复的元素

遍历list

第一种

for(auto it = L.begin();it!=L.end();it++)
        cout<<*it<<endl;

第二种

for (auto e:L) {
        cout << e << endl;//auto循环更方便
    }

erase

erase 是删除之后会返回下一个位置。

cur = L.erase(cur);
//会讲 cur位置的元素删除掉,然后返回下一个位置的迭代器

insert

insert插入的是在当前位置的前一个位置,同时插入后返回插入位置的迭代器。

cur =  L.insert(cur,x);

splice

作用是将另一个list中的元素复制

 ans[t].splice(ans[t].end(),ans[s]);

queue

常用函数

1.入队:如q.push(x):将x元素接到队列的末端;

2.出队:如q.pop() 弹出队列的第一个元素,并不会返回元素的值;

3,访问队首元素:如q.front()

4,访问队尾元素,如q.back();

5,访问队中的元素个数,如q.size();

priority_queue

priority_queue常用函数

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

大根堆,小根堆

默认是大顶堆


一般是:

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

// 也可以通过重载运算符来得到想要的根堆。

set

set常用函数

有一个multiset 是它的兄弟,区别是里边的元素可以是重复的,在函数使用上基本上是一样的,如erase,set删除的是单个,multiset 删除的是所有相同的。

begin();            // 返回指向第一个元素的迭代器
end();              // 返回指向迭代器的最末尾处(即最后一个元素的下一个位置)
clear();            // 清除所有元素
count();            // 返回某个值元素的个数
 
empty();            // 如果集合为空,返回true
 
equal_range();      //返回集合中与给定值相等的上下限的两个迭代器
 
erase()–删除集合中的元素
 
find()–返回一个指向被查找到元素的迭代器
 
get_allocator()–返回集合的分配器
 
insert()–在集合中插入元素
 
lower_bound()–返回指向大于(或等于)某值的第一个元素的迭代器
 
key_comp()–返回一个用于元素间值比较的函数
 
max_size()–返回集合能容纳的元素的最大限值
 
rbegin()–返回指向集合中最后一个元素的反向迭代器
 
rend()–返回指向集合中第一个元素的反向迭代器
 
size()–集合中元素的数目
 
swap()–交换两个集合变量
 
upper_bound()–返回大于某个值元素的迭代器
 
value_comp()–返回一个用于比较元素间的值的函数

find()

find()返回的是一个迭代器位置,如果没有找到则是end()

auto it = ans.find(n);
            if(it!=ans.end())
            cout<<1<<endl;
            else
            cout<<0<<endl;

erase()

erase() 先通过 find()函数找到x元素的迭代器位置。如果不是end()就删除
注意:set中的erase()无返回值。

if(it!=ans.end())
            ans.erase(it);

set取并集,交集,差集

基本介绍
set里面有set_intersection(取集合交集)、set_union(取集合并集)、set_difference(取集合差集)、set_symmetric_difference(取集合对称差集)等函数。

set_union

set_union(A.begin(),A.end(),B.begin(),B.end(),inserter(result,result.begin()));
    for(int i=0;i<result.size();i++)
    {
        cout<<result[i]<<" ";
    }

set_intersection

set_intersection(A.begin(),A.end(),B.begin(),B.end(),inserter(result,result.begin()));
    for(int i=0;i<result.size();i++)
    {
        cout<<result[i]<<" ";
    }

set_difference

set_difference(A.begin(),A.end(),B.begin(),B.end(),inserter(result,result.begin()));
    for(int i=0;i<result.size();i++)
    {
        cout<<result[i]<<" ";
    }

注意事项

与 map/multimap 不同的是,map/multimap中存储的是真正的键值对<key,value>,set 中只放 value,但与底层实际存放的是由<value,value>构成的键值对;
set中插入元素时,只需要插入 value 即可,不需要构造键值对;
set中的元素不可以重复;
使用set 的迭代器遍历 set中的元素,可以得到有序序列;
set中的元素默认按照小于来比较
set中查找某个元素,时间复杂度为:log2N;

代码:

int main()
{
    while(~scanf("%d",&q)){
        multiset<int>ans;
        while(q--){
        scanf("%d%d",&fg,&n);
        if(fg == 0){
            ans.insert(n);
            int len = ans.size();
            printf("%d\n",len);
        }else if(fg == 1){
            int state = ans.count(n);
            printf("%d\n",state);
        }else if(fg == 2)
            ans.erase(n);
        else{
            int r;
            cin>>r;
            auto left = ans.lower_bound(n);
            while(left!=ans.end()&&*left<=r)
            {
                printf("%d\n",*left);
            left++;
        }
    }
    }
    }
    return 0;
}

bitset

1、构造函数:

#include<bitset>
std::bitset<4> foo; //创建一个4位的位集,每一位默认为0
当整数的大小小于位数时,高位填充为0
std::bitset<4> foo(5);  //用整数初始化  5二进制位:101    foo值:0101
当整数的大小超过位数时,从整数二进制的低位开始赋值,高位被舍弃
std::bitset<4> foo(19);  //用整数初始化,19二进制位:10011     foo值:1100
std::bitset<4> foo(std:;string("0101")); //字符串初始化,字符串中必须只能含有‘0’/‘1’

2、常用操作:

位运算都可以用: 与、或、非、异或,左移,右移
foo&foo2
foo|foo2
~foo
foo^foo2
foo<<=2
foo>>=2
foo.size() 返回大小(位数)
foo.count() 返回1的个数
foo.any() 返回是否有1
foo.none() 返回是否没有1
foo.set() 全都变成1
foo.set(p) 将第p + 1位变成1
foo.set(p, x) 将第p + 1位变成x
foo.reset() 全都变成0
foo.reset(p) 将第p + 1位变成0
foo.flip() 全都取反
foo.flip(p) 将第p + 1位取反
foo.to_ulong() 返回它转换为unsigned long的结果,如果超出范围则报错
foo.to_ullong() 返回它转换为unsigned long long的结果,如果超出范围则报错
foo.to_string() 返回它转换为string的结果
b[pos] :访问b中在pos处的二进制位
b.test(pos) : 	b中在pos处的二进制位是否为1?
b.set(pos) 	把b中在pos处的二进制位置为1
b.reset(pos) 把b中在pos处的二进制位置为0

例子

int main()
{
   while(~scanf("%d",&q)){
       bitset<64>ans(0);
       while(q--){
           scanf("%d",&fg);
           if(fg == 0){
               scanf("%d",&n);
               cout<<ans[n]<<endl;
           }else if(fg == 1){
               scanf("%d",&n);
               ans.set(n);
           }else if(fg == 2){
               scanf("%d",&n);
               ans.reset(n);
           }
           else if(fg == 3){
               scanf("%d",&n);
               ans.flip(n);
           }
           else if(fg == 4){
               if(ans.count() == 64)
               printf("1\n");
               else
               printf("0\n");
           }
           else if(fg == 5){
               if(ans.any())
               printf("1\n");
               else
               printf("0\n");
           }
           else if(fg == 6){
                if(ans.none())
               printf("1\n");
               else
               printf("0\n");
               
           }else if(fg == 7){
               cout<<ans.count()<<endl;
           }else{
               cout<<ans.to_ullong()<<endl;
           }
       }
   }
    return 0;
}

string

数字的字典序比较

难点是将数字转化为字符,对于1位的加‘0’即可,但多位数的就不好处理,因此可以直接读入字符串。

int main()
{
    string s1,s2,s;
   cin>>n;
   for(int i=0;i<n;++i)
   cin>>s,s1 += s;
   cin>>m;
   for(int i=0;i<m;++i)
   cin>>s,s2 += s;
   if(s2>s1)
   cout<<1<<endl;
   else
   cout<<0<<endl;
   
   return 0;
}

map

map的基本操作函数

C++ Maps是一种关联式容器,包含“关键字/值”对
      begin()          返回指向map头部的迭代器
      clear()         删除所有元素
      count()          返回指定元素出现的次数
      empty()          如果map为空则返回true
      end()            返回指向map末尾的迭代器
      equal_range()    返回特殊条目的迭代器对
      erase()          删除一个元素
      find()           查找一个元素
      get_allocator()  返回map的配置器
      insert()         插入元素
      key_comp()       返回比较元素key的函数
      lower_bound()    返回键值>=给定元素的第一个位置
      max_size()       返回可以容纳的最大元素个数
      rbegin()         返回一个指向map尾部的逆向迭代器
      rend()           返回一个指向map头部的逆向迭代器
      size()           返回map中元素的个数
      swap()            交换两个map
      upper_bound()     返回键值>给定元素的第一个位置
      value_comp()      返回比较元素value的函数

erase() 删除元素

  • size_t erase( const key_type& key );
    根据key来进行删除, 返回删除的元素数量,在map里结果非0即1
  • iterator erase( iterator pos )
    删除迭代器指向位置的键值对,并返回一个指向下一元素的迭代器
  • iterator erase( const_iterator first, const_iterator last );
    删除一定范围内的元素,并返回一个指向下一元素的迭代器

注意事项

  • 使用insert方法插入的时候,如果键存在,不会覆盖原来的值,用数组的方式才可以。
  • 还有一个很重要的点就是,如果访问了一个不存在的键,那么会返回0之后会自动创建这个键。
    因此可以如下来解决
cin>>s;
                if(!ans.count(s))
                cout<<0<<endl;
                else
                printf("%d\n",ans[s]);

multimap

multimap容器保存的是有序的键/值对,但是可以保存重复的元素。multimap中会出现具有相同键值的元素序列。multimap大部分成员函数的使用方式和map相同。因为重复键的原因,multimap有一些函数的使用方式和map有一些区别。

访问元素

单个find()

multimap 的成员函数 find() 可以返回一个键和参数匹配的元素的迭代器。

std::multimap<std::string, size_t> people {{"Ann",25},{"Bill", 46}, {"Jack", 77}, {"Jack", 32},{"Jill", 32}, {"Ann", 35} };
std::string name {"Bill"};
auto iter = people.find(name);
if (iter ! = std::end (people))
    std::cout << name << " is " << iter->second << std::endl;
iter = people.find ("Ann");
if (iter != std::end(people))
    std::cout << iter->first << " is " << iter->second <<std::endl;

equal_range

如果我们想访问给定键对应的所有元素。成员函数 equal_range() 就可以做到这一点。它会返回一个封装了两个迭代器的 pair 对象,这两个迭代器所确定范围内的元素的键和参数值相等。例如:

auto pr = people.equal_range("Ann");
if(pr.first != std::end(people))
{
    for (auto iter = pr.first ; iter != pr.second; ++iter)
        std:cout << iter->first << " is " << iter->second << std::endl;
}

insert()

只能使用insert来插入元素
例如:

ans.insert(make_pair(s,x));

reverse

区间是左闭右开的。

reverse函数用于反转在**[first,last)**范围内的顺序(包括first指向的元素,不包括last指向的元素),reverse函数无返回值

rotate

template <class ForwardIterator>
  void rotate (ForwardIterator first, ForwardIterator middle,
               ForwardIterator last);

官方手册

全排列函数

头文件:#include
函数模板:next_permutation(arr, arr+size);
函数模板:prev_permutation(arr, arr+size);
解释:arr为数组,size为数组长度。next_permutation(arr, arr+size);当有下一个较大值返回1,否则返回0,prev_permutation(arr, arr+size);当有上一个较小值返回1,否则返回0。例如:3 2 1,只有上一个较小值,没有下一个较大值。1 2 3只有下一个较大值,没有上一个较小值。2 1 3 的上一个较小值为 1 3 2,下一个较大值为 2 3 1.明白了吧!然后看下代码,怎么去用:

includes(子集)

在stl中有一个includes函数,对于vector来说,有v1和v2,如果判断v1里面的所有元素是否被v2所包含,则可以使用

includes(begin(v1),end(v1),begin(v2),end(v2))  

如果v1包含v2则会返回true。
注意使用前提是必须先进行排序
即sort(begin(v1),end(v1)) sort(begin(v2),end(v2))

二分查找

首先数组必须是有序的!

1.binary_search()(查找某个值在数组中是否存在)

使用方法:binary_search(list,list+n,a)

list为数组,a为要查询的值,n为数组大小

binary_search返回的是真假值,就是它只判断这个数组中是否存在这个数;

2. lower_bound查找第一个大于或等于某个元素的位置

使用方法:lower_bound(list,list+n,a)

list为数组,n为数组大小,a为要查询的值

注意事项:lower_bound()返回的是指针,所以所以减去数组的指针就是int变量了

3.upper_bound查找第一个大于某个元素的位置。

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

落春只在无意间

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值