SGU155(笛卡尔树的构造)
题目:http://acm.sgu.ru/problem.php?contest=0&problem=155
题意:给出每个点的两个值key和fix,且所有的key值和fix值都是不相同的,要求构造出笛卡尔树。输入每个点的两个权
值,输出笛卡尔树每个结点(按照输入的顺序编号)的父亲结点和两个儿子的编号。
分析:首先,笛卡尔树对于key来说是二叉搜索树,对于fix来说是最小堆,所以跟Treap一样。笛卡尔树在LCA和RMQ问题中有
着重要的应用。这题首先记录下每个结点的ID,然后以key为关键字排序。排完了之后就会有线性的构造笛卡尔树的算法了。
这里的笛卡尔树一定是存在的,所以先输出YES。
构造笛卡尔树的过程:
使用数据结构栈,栈中保存的始终是右链,即根结点、根结点的右儿子、根结点的右儿子的右儿子……组成的链,并且栈中从
栈顶到栈底key依次减小。
如果按照从后到前的顺序判断一个元素是否大于a[i],则每次插入的时间复杂度为O(k+1),k为本次插入中移除的右链元素个
数。因为每个元素最多进出右链各一次,所以整个过程的时间复杂度为O(n)。
#include <iostream>
#include <string.h>
#include <algorithm>
#include <stdio.h>
using namespace std;
const int N=1000005;
const int INF=~0U>>1;
struct node
{
int id; //id记录节点的编号,从1开始
int key,fix; //二元组
int pre,l,r; //分别表示当前节点的父亲,左儿子和右儿子
void clear()
{
pre=l=r=0;
}
bool operator < (node t) const
{
return key<t.key;
}
};
node T[N];
int stack[N],p[N],top;
void Init(int n)
{
for(int i=1; i<=n; i++)
T[i].pre=T[i].l=T[i].r=0;
T[0].fix=-INF;
}
int Build(int n)
{
top=0;
stack[++top]=1;
for(int i=2; i<=n; i++)
{
while(top>=0&&T[i].fix<T[stack[top]].fix)
--top;
if(top)
{
T[i].pre=stack[top];
T[i].l=T[stack[top]].r;
T[T[stack[top]].r].pre=i;
T[stack[top]].r=i;
stack[++top]=i;
}
else
{
T[stack[1]].pre=i;
T[i].l=stack[1];
stack[++top]=i;
}
}
return stack[1];
}
int main()
{
int n;
scanf("%d",&n);
Init(n);
for(int i=1; i<=n; i++)
{
scanf("%d%d",&T[i].key,&T[i].fix);
T[i].id=i;
}
sort(T+1,T+n+1);
int root=Build(n);
for(int i=1; i<=n; i++)
p[T[i].id]=i;
puts("YES");
for(int i=1; i<=n; i++)
printf("%d %d %d\n",T[T[p[i]].pre].id,T[T[p[i]].l].id,T[T[p[i]].r].id);
return 0;
}
SGU155(笛卡尔树的构造)相关推荐
- POJ1785(笛卡尔树的构造)
题目:http://poj.org/problem?id=1785 题意:构造笛卡尔树,这里是最大堆构造,然后以广义表的形式输出这棵笛卡尔树. #include <iostream> #i ...
- CF1580B Mathematics Curriculum(笛卡尔树、树形dp)
解析 比较巧妙的一道题. 难点在于对题意的转化. 关键性质:符合要求的点等价于与笛卡尔树上深度为 mmm 的点. 原因也较为显然,考虑一个特定的点 xxx,当枚举全局最大值时,其会对 xxx 产生贡献 ...
- POJ - 2201 Cartesian Tree(笛卡尔树-单调栈/暴跳父亲)
题目链接:点击查看 题目大意:给出n个节点的key和val,构造出其笛卡尔树的原型 笛卡尔树的定义: 所谓笛卡尔树,就是将给定的n个二元组(key,val)建成一棵树.使得: 如果只关注key,那么这 ...
- 笛卡尔树详解带建树模板及例题运用(Largest Submatrix of All 1’s,洗车 Myjnie,Removing Blocks,SPOJ PERIODNI)
文章目录 笛卡尔树 介绍 例题 Largest Submatrix of All 1's 应用 「POI2015」洗车 Myjnie [AGC028B] Removing Blocks SPOJ PE ...
- YbtOJ#20240-[冲刺NOIP2020模拟赛Day10]弱者对决【笛卡尔树,区间dp】
正题 题目链接:https://www.ybtoj.com.cn/contest/68/problem/4 题目大意 mmm个三元组(ai,bi,ci)(a_i,b_i,c_i)(ai,bi,ci ...
- Moles(笛卡尔树 Z Algorithm)
original link - http://poj.org/problem?id=4005 题意: 有n个数,按照给出的顺序依次插入二叉搜索树,然后从小到大遍历(从根开始往下走,最后回来),路过的点 ...
- 笛卡尔树(Cartesian Tree)
一.简介 笛卡尔树是一种特定的二叉树数据结构,由数组存储.在范围最值.范围top k查询方面广泛应用. 笛卡尔树的性质: 树中的元素满足二叉搜索树性质,要求按照中序遍历得到的序列为原数组序列 树中节点 ...
- 笛卡尔树简介(分类到treap里面)
笛卡尔树结构由Vuillmin在解决范围搜索的几何数据结构问题时提出的,从数列中构造一棵笛卡尔树可以线性时间完成,需要采用基于栈的算法来找到在该数列中的所有最近小数.由此可知,笛卡尔树是一种特定的二叉 ...
- HDU 6305 RMQ Similar Sequence(笛卡尔树)
题目链接:RMQ Similar Sequence 题意 首先给定一个长度为 nnn 的整数序列 A={a1,a2,⋯,an}" role="presentation" ...
最新文章
- SAP登陆界面TITLE修改方法(Method of SAP Logon GUI Title Modification)
- dw1000信标码_DW1000方案工牌型UWB标签,助力10厘米高精度室内定位!
- 从云服务器上拷贝文件,从云服务器上拷贝文件
- 基于JAVA+SpringMVC+Mybatis+MYSQL的会议室预约管理系统
- oracle中查找某用户执行某张表的操作操作记录
- BCH又要分叉?这一次社区似乎喜闻乐见
- 【历史上的今天】7 月 18 日:英特尔成立;万维网上传了第一张照片;eBay 分拆 PayPal
- python_pygame_alpha-beta剪枝算法_玩中国象棋
- 论文笔记 Dependent Gaussian Processes 相关高斯过程
- 攻防世界_Crypto_Decrypt-the-Message
- 研究生招生信息网服务器异常,2012研究生网上报名常见问题汇总
- HIVE学习系列——Hive操作
- 如何使用html+Chart画甜甜圈图
- 初三计算机课程试题,中考信息技术试题
- 使用python 实现 微信好友 个性签名 并 制作 词云图
- 【Metal2剖析(四):基于MPS的GPU加速光线追踪(Accelerating Ray Tracing)】
- jenkin+docker 构建项目
- android经纬度转wev墨卡托,GPS工具箱批量导入经纬度教程.docx
- fbd 文件的研究笔记
- lnmp搭建qq农场(小白教程)
热门文章
- Spring容器初始化实现V2 版本
- Redis中的可用性保证之Sentinel 原理
- Ant Design入门之介绍
- SpringBoot_web开发-webjars静态资源映射规则
- FastDFS_install_document_detail
- Android从url不产生cookie,如何从android.webkit.CookieManager获取所有cookie或cookie的URL
- 深入理解Kafka(1)
- oracle 11.2 安装asm,oracle11r2安装asm+rac配置步骤.doc
- python集合属性方法运算_python对象及运算 序列小结 集合
- Flask中的请求上下文和应用上下文