C++ __gnu_pbds(hash,可并堆,平衡树)

pb_ds 是GNU-C++自带的一个C++的扩展库,其中实现了很多数据结构,比STL里面的功能更强大

#include<ext/pb_ds/assoc_container.hpp>
#include<ext/pb_ds/tree_policy.hpp>   // 用tree
#include<ext/pb_ds/hash_policy.hpp>   // 用hash
#include<ext/pb_ds/trie_policy.hpp>   // 用trie
#include<ext/pb_ds/priority_queue.hpp>// 用priority_queue
using namespace __gnu_pbds;
---
#include<bits/extc++.h>
using namespace __gnu_pbds;
//bits/extc++.h与bits/stdc++.h类似,bits/extc++.h是所有拓展库,bits/stdc++.h是所有标准库

哈希表

其中cc开头为拉链法,gp开头为探测法,个人实测探测法稍微快一些。

啥?操作?其实就和map差不多,支持[ ]和find。

#include<ext/pb_ds/assoc_container.hpp>
#include<ext/pb_ds/hash_policy.hpp>
using namespace __gnu_pbds;cc_hash_table<string,int>mp1;//拉链法
gp_hash_table<string,int>mp2;//查探法(快一些)

说明:

在不允许使用C++11的时候,pb_ds库中的两种hash函数比map的效率大大提高 ,可以代替map作为一个哈希工具,使用方法和map完全一样,一般来说查探法的效率更高

可并堆

需要的头文件:

用法和普通的优先队列一样

#include<ext/pb_ds/priority_queue.hpp>
using namespace __gnu_pbds;
__gnu_pbds::priority_queue<int>q;//因为放置和std重复,故需要带上命名空间
__gnu_pbds::priority_queue<int,greater<int>,pairing_heap_tag> q;//最快
__gnu_pbds::priority_queue<int,greater<int>,binary_heap_tag> q;
__gnu_pbds::priority_queue<int,greater<int>,binomial_heap_tag> q;
__gnu_pbds::priority_queue<int,greater<int>,rc_binomial_heap_tag> q;
__gnu_pbds::priority_queue<int,greater<int>,thin_heap_tag> q;
__gnu_pbds::priority_queue<int,greater<int> > q;

pb_ds库的堆提供了五种tag,分别是binary_heap_tagbinomal_heap_tagpairing_heap_tagthin_heap_tagrc_binomal_heap_tag。 因为重名的原因一定要加上 __gnu_pbds::
在这里插入图片描述

常用操作:

push()  //会返回一个迭代器
top()    //同 STL
size()   //同 STL 
empty()  //同 STL 
clear()  //同 STL 
pop()    //同 STL 
join(priority_queue &other)            //合并两个堆,other会被清空
split(Pred prd,priority_queue &other)  //分离出两个堆
modify(point_iterator it,const key)    //修改一个节点的值

平衡树

#include<ext/pb_ds/assoc_container.hpp>
#include<ext/pb_ds/hash_policy.hpp>using namespace __gnu_pbds;
template<typename T>
using ordered_set = tree<T,null_type,less<T>,rb_tree_tag,tree_order_statistics_node_update>;// rb_tree_tag 和 splay_tree_tag 选择树的类型(红黑树和伸展树)
T // 自定义数据类型
null_type//无映射(老版本g++为null_mapped_type)
less<T>//Node的排序方式从小到大排序
tree_order_statistics_node_update//参数表示如何更新保存节点信息 tree_order_statistics_node_update会额外获得order_of_key()和find_by_order()两个功能。ordered_set<Node> Tree;  // Node 自定义struct 注意重载less
Tree.insert(Node);       // 插入
Tree.erase(Node);        // 删除
Tree.order_of_key(Node); // 求Node的排名:当前数小的数的个数 +1
Tree.find_by_order(k);   // 返回排名为k+1的iterator 即有k个Node比*it小
Tree.join(b);            // 将b并入Tree,前提是两棵树类型一致并且二没有重复元素
Tree.split(v, b);        // 分裂,key小于等于v的元素属于Tree,其余属于b
Tree.lower_bound(Node);  // 返回第一个大于等于x的元素的迭代器
Tree.upper_bound(Node);  // 返回第一个大于x的元素的迭代器//以上的所有操作的时间复杂度均为O(logn)
//注意,插入的元素会去重,如set
ordered_set<T>::point_iterator it=Tree.begin();  // 迭代器
//显然迭代器可以++,--运算

P3369 【模板】普通平衡树

因为tree里不能有相同的数,但是实际会插入相同的数,所以把这些数左移20位在加上一个常数操作(n<220n<2^{20}n<220,如果a<ba<ba<b,那么一定有{(a<<20)+n}<{b<<20}\{(a<<20) +n\}<\{b<<20\}{(a<<20)+n}<{b<<20},这样就保证了在不影响相对大小关系的情况下,消除了相同的数。

别的操作看代码就可以理解了,非常巧妙的搞定了相同数的情况。

rb_tree_tag

#include<bits/stdc++.h>
#include<ext/pb_ds/tree_policy.hpp>
#include<ext/pb_ds/assoc_container.hpp>
using namespace std;
using namespace __gnu_pbds;
using ll=long long;template <class T=int> T rd()
{T res=0;T fg=1;char ch=getchar();while(!isdigit(ch)) {if(ch=='-') fg=-1;ch=getchar();}while( isdigit(ch)) res=(res<<1)+(res<<3)+(ch^48),ch=getchar();return res*fg;
}
template<typename T>
using ordered_set = tree<T,null_type,less<T>,rb_tree_tag,tree_order_statistics_node_update>;const int N=100010;
int n,m;
ll k,ans;
ordered_set<ll> T;
int main()
{n=rd();for(int i=1;i<=n;i++){int op=rd();k=rd<ll>();if(op==1) T.insert((k<<20)+i);if(op==2) T.erase(T.lower_bound(k<<20));if(op==3) printf("%d\n",T.order_of_key((k<<20))+1);if(op == 4)ans=*T.find_by_order(k-1),printf("%lld\n",ans>>20);if(op == 5)ans=*--T.lower_bound(k<<20),printf("%lld\n",ans>>20);if(op == 6)ans=*T.upper_bound((k<<20)+n),printf("%lld\n",ans>>20);}return 0;
}

splay_tree_tag

Code from

#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <algorithm>
#include <map>
#include <ext/pb_ds/assoc_container.hpp> 
using namespace std;
using namespace __gnu_pbds;
#define Node pair<int,int>
map <int,int> s;
tree< Node ,null_type,less< Node >,splay_tree_tag,tree_order_statistics_node_update> T;
int n,op,x;
int main()
{scanf("%d",&n);for(register int i = 1; i <= n; i++)switch(scanf("%d%d",&op,&x), op){case 1 :T.insert(Node(x,s[x]++));break;case 2 :T.erase(Node(x,--s[x]));break;case 3 :printf("%d\n",(int)T.order_of_key(Node(x,0))+1);break;case 4 :printf("%d\n",T.find_by_order(x-1)->first);break;case 5 :printf("%d\n",T.find_by_order(T.order_of_key(Node(x,0))-1)->first);break;case 6 :printf("%d\n",T.find_by_order(T.order_of_key(Node(x,s[x]-1))+(T.find(Node(x,0)) == T.end() ? 0 : 1))->first);break;default:break;}return 0;
}

底层代码


参考以及进阶

比STL还STL?——平板电视
pb_ds库的一些常用方法
C++ __gnu_pbds(平板电视)超详细教程(C++内置的平衡树,字典树,hash)

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/318671.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

理解至上:二叉堆与优先队列详细用法

文章目录二叉堆概述插入代码访问代码完整代码优先队列&#xff1a;priority_queue基本用法小根堆的声明&#xff1a;结构体注意Thanks for reading&#xff01;二叉堆 概述 为什么不用pq呢 算比较简单的数据结构了 它可以用log的时间复杂度插入元素和访问&#xff08;取出&am…

AT5661-[AGC040C]Neither AB nor BA【模型转换】

正题 题目链接:https://www.luogu.com.cn/problem/AT5661 题目大意 一个包含A,B,CA,B,CA,B,C的序列&#xff0c;每次可以选择相邻的两个除了ABABAB和BABABA的删去。 求有多少个长度为NNN的序列可以删完。 1≤N≤1071\leq N\leq 10^71≤N≤107 解题思路 因为每次是删除一个奇…

牛客题霸 [矩阵的最小路径和] C++题解/答案

牛客题霸 [矩阵的最小路径和] C题解/答案、 题目描述 给定一个 n * m 的矩阵 a&#xff0c;从左上角开始每次只能向右或者向下走&#xff0c;最后到达右下角的位置&#xff0c;路径上所有的数字累加起来就是路径和&#xff0c;输出所有的路径中最小的路径和。 题解&#xff…

2021牛客暑期多校训练营7 B-xay loves monotonicity(线段树+不降子序列)

P4198 楼房重建 线段树维护以某点为开头的最长不下降子序列 使用下面calc函数能够计算线段树u维护的区间中&#xff0c;以x为开头最长不下降子序列的个数。 calc需要维护区间最值。 template<typename T> int calc(int u,T x) {if(tree[u].ltree[u].r) return tree[u]…

不止代码:最长上升序列

文章目录题目描述样例解析仔细审题&#xff01;&#xff01;&#xff01;&#xff01;代码题目描述 给定一个序列 求出它的单调上升序列长度并输出这个序列 样例 in: 13 7 9 16 38 24 37 18 44 19 21 22 63 15 out&#xff1a; max8 7 9 16 18 19 21 22 63解析 这题我一开始…

AT2305-[AGC010D]Decrementing【博弈论】

正题 题目链接:https://www.luogu.com.cn/problem/AT2305 题目大意 nnn个数字两个人进行博弈&#xff0c;每个人的操作为 选择一个大于1的数字减一之后所有数字除以所有数字的gcdgcdgcd 无法操作者败&#xff0c;保证初始所有数字互质 求是否先手必胜 1≤n≤1051\leq n\leq…

牛客题霸 [删除链表的倒数第n个节点] C++题解/答案

牛客题霸 [删除链表的倒数第n个节点] C题解/答案 题目描述 给定一个链表&#xff0c;删除链表的倒数第n个节点并返回链表的头指针 例如&#xff0c; 给出的链表为:1->2->3->4->5, n 2. 删除了链表的倒数第n个节点之后,链表变为1->2->3->5. 备注&#xf…

2021牛客暑期多校训练营7 K-xay loves sequence(主席树+二分)

K-xay loves sequence 首先不考虑模kkk的限制&#xff0c;容易想到对原数组做一个差分得到diai−ai−1d_ia_i-a_{i-1}di​ai​−ai−1​&#xff0c;显然对于∀1≤i≤nai0\forall_{1\leq i\leq n} a_i0∀1≤i≤n​ai​0 等价于∀1≤i≤ndi0\forall_{1\leq i\leq n} d_i0∀1≤i…

ASP.NET Core 搭配 Nginx 的真实IP问题

一.前言Nginx&#xff08;Engine X&#xff09;是一个高性能HTTP和反向代理服务&#xff0c;是由俄罗斯人伊戈尔赛索耶夫为访问量第二的Rambler.ru站点&#xff08;俄文&#xff1a;Рамблер&#xff09;开发的&#xff0c;第一个公开版本0.1.0发布于2004年10月4日。 如果…

不止代码:保留道路(ybtoj 最小生成树)

文章目录题目描述解析代码thanks for reading!题目描述 解析 其实就是修建道路 我一开始只能想到枚举g去跑最小生成树 是m^2的算法&#xff08;50pts&#xff09; 但是其实每次加入的边只有一条 而且之前都不在最小生成树上的边以后也肯定不会在 所以可以建一个新的边的集合存…

P7515-[省选联考 2021A卷]矩阵游戏【差分约束】

正题 题目链接:https://www.luogu.com.cn/problem/P7515 题目大意 有一个n∗mn*mn∗m的矩形AAA&#xff0c;然后给出一个(n−1)∗(m−1)(n-1)*(m-1)(n−1)∗(m−1)的矩形BBB满足 Bi,jAi,jAi1,jAi,j1Ai1,j1B_{i,j}A_{i,j}A_{i1,j}A_{i,j1}A_{i1,j1}Bi,j​Ai,j​Ai1,j​Ai,j1​…

牛客题霸 [链表中环的入口节点] C++题解/答案

牛客题霸 [链表中环的入口节点] C题解/答案 题目描述 对于一个给定的链表&#xff0c;返回环的入口节点&#xff0c;如果没有环&#xff0c;返回null 拓展&#xff1a; 你能给出不利用额外空间的解法么&#xff1f; 题解&#xff1a; 判断环有个很巧妙的方法&#xff0c;之…

2021牛客暑期多校训练营8 F-Robots(bitset优化dp)

F-Robots 第一种第二种机器人直接O(n)O(n)O(n)判断即可。 第三种机器人暴力dp&#xff0c;用bitset优化。 bitset<250005> b[i][j] 表示从(i,j)(i,j)(i,j)能到达哪些点&#xff0c;第三种机器人向右向下转移即可。 状态压缩&#xff01; 时间复杂度O(qnn4w)O(qn\frac{…

不止代码:路径数量(ybtoj-最小生成树)

文章目录题目描述解析代码题目描述 解析 乍一看&#xff1a;是个水题啊&#xff01; 显然如果途径存在强连通的点&#xff0c;路径就会变为正无穷 所以缩点加拓扑dp以及一些特判应该就可以解决了&#xff01; 一交&#xff1a;40分。。。 然后就开始拆东墙补西墙的debug。。。…

重磅!!!微软发布.NET Core 2.2

我们很高兴地宣布发布.NET Core 2.2。它包括对运行时的诊断改进&#xff0c;对ARM32 for Windows和Azure Active Directory for SQL Client的支持。此版本中最大的改进是在ASP.NET Core中。ASP.NET Core 2.2和Entity Framework Core 2.2。您可以在Windows&#xff0c;macOS和Li…

Loj#2769-「ROI 2017 Day 1」前往大都会【最短路树,斜率优化】

正题 题目链接:https://loj.ac/p/2769 题目大意 给出nnn个点mmm条地铁线路&#xff0c;每条线路是一条路径。 求111到nnn的最短路且在最短路径的情况下相邻换乘点的距离平方和最大。 1≤n,m,∑si≤1061\leq n,m,\sum s_i\leq 10^61≤n,m,∑si​≤106 解题思路 首先肯定是在…

牛客题霸 [两个链表生成相加链表] C++题解/答案

牛客题霸 [两个链表生成相加链表] C题解/答案 题目描述 假设链表中每一个节点的值都在 0 - 9 之间&#xff0c;那么链表整体就可以代表一个整数。 给定两个这种链表&#xff0c;请生成代表两个整数相加值的结果链表。 例如&#xff1a;链表 1 为 9->3->7&#xff0c;链…

2021牛客暑期多校训练营8 J-Tree(思维dp+rmq)

J-Tree Cosmic_Tree题解 赛时队友想到了预处理s→ts\to ts→t路径上的点最远到达的点&#xff0c;后面贪心做的一直wa。正解是dp。 下面的solve(l,r,op)\text{solve}(l,r,\text{op})solve(l,r,op)函数中&#xff0c;当lrlrlr时不满足题意不合法&#xff0c;当op0\text{op}0op…

[翻译] ASP.NET Core 2.2 正式版发布

本文为翻译&#xff0c;原文地址&#xff1a;https://blogs.msdn.microsoft.com/webdev/2018/12/04/asp-net-core-2-2-available-today/我&#xff08;文章作者&#xff09;很高兴地宣布ASP.NET Core 2.2现在作为.NET Core 2.2的一部分提供&#xff01;怎么获取它您可以从 .NET…

理解至上:数位dp(ybtoj-B数计数)

文章目录简要题目描述解析dp定义:试填法代码thanks for reading&#xff01;简要 数位dp&#xff0c;天下第一 最重要的应该有两个&#xff1a; 1.状态转移式的确定 2.试填法不断往后模拟 &#xff08;至今是唯一一道数位dp&#xff0c;究竟重要的是啥我其实也没有太多经验 &am…