题解 洛谷 P3521 【[POI2011]ROT-Tree Rotations】
给定一棵二叉树,叶子节点有权值,可以进行若干次交换一个节点的左右儿子的操作,使前序遍历叶子的逆序对最少。
考虑一个节点下子树逆序对的产生:
① 只在左子树中产生。
② 只在右子树中产生。
③ 在左子树和右子树中交叉产生。
因为二叉树的性质,所以 ① ② 两种情况只需递归下去求解,只需考虑情况 ③ 。
用权值线段树来记录信息,通过线段树合并来统计答案。
具体实现细节看代码吧。
记得开\(long\ long\)。
\(code:\)
#include<bits/stdc++.h>
#define maxn 10000010
using namespace std;
typedef long long ll;
template<typename T> inline void read(T &x)
{
x=0;char c=getchar();bool flag=false;
while(!isdigit(c)){if(c=='-')flag=true;c=getchar();}
while(isdigit(c)){x=(x<<1)+(x<<3)+(c^48);c=getchar();}
if(flag)x=-x;
}
int n,root,tree_cnt;
ll s1,s2,ans;
bool vis[maxn];
int ls[maxn],rs[maxn],rt[maxn];
ll siz[maxn];
void pushup(int cur)
{
siz[cur]=siz[ls[cur]]+siz[rs[cur]];
}
void modify(int L,int R,int pos,int &cur)
{
if(!cur) cur=++tree_cnt;
if(L==R)
{
siz[cur]++;
return;
}
int mid=(L+R)>>1;
if(pos<=mid) modify(L,mid,pos,ls[cur]);
if(pos>mid) modify(mid+1,R,pos,rs[cur]);
pushup(cur);
}
int merge(int x,int y)
{
if(!x||!y) return x+y;
s1+=siz[ls[x]]*siz[rs[y]];
s2+=siz[ls[y]]*siz[rs[x]];
ls[x]=merge(ls[x],ls[y]);
rs[x]=merge(rs[x],rs[y]);
pushup(x);
return x;
}
void dfs(int &x)
{
int val;
read(val);
x=++tree_cnt;
if(!val) dfs(ls[x]),dfs(rs[x]);
else vis[x]=true,modify(1,n,val,rt[x]);
}
void work(int x)
{
if(vis[x]) return;
work(ls[x]),work(rs[x]),s1=s2=0;
rt[x]=merge(rt[ls[x]],rt[rs[x]]);
ans+=min(s1,s2);
}
int main()
{
read(n);
dfs(root);
work(root);
printf("%lld\n",ans);
return 0;
}
题解 洛谷 P3521 【[POI2011]ROT-Tree Rotations】的更多相关文章
- 洛谷 P3521 [POI2011]ROT-Tree Rotations 解题报告
P3521 [POI2011]ROT-Tree Rotations 题意:递归给出给一棵\(n(1≤n≤200000)\)个叶子的二叉树,可以交换每个点的左右子树,要求前序遍历叶子的逆序对最少. 大体 ...
- [洛谷P3521][POI2011]ROT-Tree Rotations
题目大意:给一棵$n(n\leqslant2\times10^5)$个叶子的二叉树,可以交换每个点的左右子树,要求前序遍历叶子的逆序对最少.输出最少的逆序对个数 题解:线段树合并,对于每个节点求出交换 ...
- 洛谷P3521 [POI2011]ROT-Tree Rotation [线段树合并]
题目传送门 Tree Rotation 题目描述 Byteasar the gardener is growing a rare tree called Rotatus Informatikus. I ...
- 洛谷P3513 [POI2011]KON-Conspiracy
洛谷P3513 [POI2011]KON-Conspiracy 题目描述 Byteotia的领土被占领了,国王Byteasar正在打算组织秘密抵抗运动. 国王需要选一些人来进行这场运动,而这些人被分为 ...
- BZOJ2212或洛谷3521 [POI2011]ROT-Tree Rotations
BZOJ原题链接 洛谷原题链接 线段树合并裸题. 因为交换子树只会对子树内部的逆序对产生影响,所以我们计算交换前的逆序对个数和交换后的个数,取\(\min\)即可. 对每个叶子节点建一棵动态开点线段树 ...
- [洛谷P3527] [POI2011]MET-Meteors
洛谷题目链接:[POI2011]MET-Meteors 题意翻译 Byteotian Interstellar Union有N个成员国.现在它发现了一颗新的星球,这颗星球的轨道被分为M份(第M份和第1 ...
- 题解 洛谷P5018【对称二叉树】(noip2018T4)
\(noip2018\) \(T4\)题解 其实呢,我是觉得这题比\(T3\)水到不知道哪里去了 毕竟我比较菜,不大会\(dp\) 好了开始讲正事 这题其实考察的其实就是选手对D(大)F(法)S(师) ...
- 题解 洛谷 P3396 【哈希冲突】(根号分治)
根号分治 前言 本题是一道讲解根号分治思想的论文题(然鹅我并没有找到论文),正 如论文中所说,根号算法--不仅是分块,根号分治利用的思想和分块像 似却又不同,某一篇洛谷日报中说过,分块算法实质上是一种 ...
- 题解-洛谷P5410 【模板】扩展 KMP(Z 函数)
题面 洛谷P5410 [模板]扩展 KMP(Z 函数) 给定两个字符串 \(a,b\),要求出两个数组:\(b\) 的 \(z\) 函数数组 \(z\).\(b\) 与 \(a\) 的每一个后缀的 L ...
随机推荐
- java基础——并发1
一.并发的定义 并发:对于这个概念一直就是没怎么搞懂,就是感觉特别的生疏,(自己从从字面上理解就是多个东西,一起出发),所以就上网上查了一些资料: 同时拥有两个或多个线程,如果程序在单核处理器上运行, ...
- Python-16-分配参数
与收集参数相反,这里用*和**分配参数 def add(x, y): return x + y 使用*分配元组 params = (1, 2) >>> ad ...
- 尚硅谷maven视频教程笔记
07.尚硅谷_Maven_部署Maven核心程序.avi 第一步先安装jdk 第二步下载maven 特别需要注意的是maven不能存储在有中文和空格的目录下面 3.调试是否安装成功,在cmd中输入 m ...
- 一条SQL删除重复记录,重复的只保留一条
情景: 我们的数据库中可能会存在很多因各种原因而重复的记录,我们需要对这些重复的记录进行删除,每组组重复的记录只保留一条就行 例如我们有这么个表:两个框框都是有重复记录的,红框和绿框都只需要留下一条, ...
- SQL注入之Union注入攻击
union联合查询算是最简单的一种注入了,但是却是经常遇到. 什么是UNION注入 UNION操作符用于合并两个或多个SELECT语句的结果集,而且UNION内部的SELECT语句必须拥有相同数量的列 ...
- JDK8--07:并行流与串行流
JDK8中,提供了并行流和串行流,使用parallel()和sequential()来处理,parallel()为并行流sequential()为串行流,两者可以相互转换,以最后一个为准 LongSt ...
- ajax前后端交互原理(6)
6.XMLHttpRequest对象 XMLHttpRequest 是一个 API,它为客户端提供了在客户端和服务器之间传输数据的功能.它提供了一个通过 URL 来获取数据的简单方式,并且不会使整个页 ...
- Security 10:权限管理
SQL Server 用于管理权限的TSQL命令有:GRANT用于授予权限,REVOKE 用于移除授予的权限,而DENY用于防止安全主体通过GRANT获得权限.但是,SQL Server的权限管理不是 ...
- asp.net core 发布包含文件
这样这个文件在发布的时候,就会包含进去了.
- ORA-04063: package body "DBSNMP.BSLN" has errors
ORA-04063: package body "DBSNMP.BSLN" has errors 问题描述: 警告日志出现报错: Sun Jun 28 00:00:01 2020 ...