HDU.1394 Minimum Inversion Number (线段树 单点更新 区间求和 逆序对)

题意分析

给出n个数的序列,a1,a2,a3……an,ai∈[0,n-1],求环序列中逆序对最少的个数。

前置技能

环序列



线段树的逆序对求法

  1. 逆序对:ai > aj 且 i < j ,换句话说数字大的反而排到前面(相对后面的小数字而言)
  2. 环序列:把第一个放到最后一个数后面,就是一次成环,一个含有n个元素序列有n个环序列。
  3. 线段树的逆序对求法:每个叶子节点保存的是当前值数字的个数。根据给出的数字,我们一次放入线段树,在放入的时候,其实考虑的是,当前线段树中比该数字大的数字个数有多少,这可以通过查询操作完成。然后我们放入线段树,每次都进行这样的操作,就可以得出一个序列的,逆序对个数。

每次进行成环的时候,就不用这么考虑了,对于一个序列,我们假设共有n个数字,并且当前的逆序对个数为k,对于第一个数字a,有t个数字小于a,可以计算得出有n-t-1个数字大于a。所以当我们把数字a移动到序列末端的时候,比他小的都成为了逆序对,比他大的都不是逆序对,此时的逆序对数目为k-t+n-t-1。

恰好此题中x[i]的值就是比他小的数字的个数,如此就可以通过简单循环完成。

代码总览

#include <bits/stdc++.h>
#define maxn 200010
#define NumMax 5000
#define ls l,m,rt<<1
#define rs m+1,r,rt<<1|1
using namespace std;
int Sum[maxn<<2],Lazy[maxn<<2];
int x[maxn];
int N;
void PushUp(int rt){
Sum[rt]=Sum[rt<<1]+Sum[rt<<1|1];
}
void Build(int l,int r,int rt){
if(l==r) {
Sum[rt] = 0;
return;
}
int m=(l+r)>>1;
Build(l,m,rt<<1);
Build(m+1,r,rt<<1|1);
PushUp(rt);
}
void UpdatePoint(int L,int l,int r,int rt){
if(l==r){
Sum[rt]++;
return;
}
int m=(l+r)>>1;
if(L <= m) UpdatePoint(L,l,m,rt<<1);
else UpdatePoint(L,m+1,r,rt<<1|1);
PushUp(rt);
}
void PushDown(int rt,int ln,int rn){
if(Lazy[rt]){
Lazy[rt<<1] = Lazy[rt];
Lazy[rt<<1|1] = Lazy[rt];
Sum[rt<<1] = Lazy[rt]*ln;
Sum[rt<<1|1] = Lazy[rt]*rn;
Lazy[rt]=0;
}
}
void UpdateInterval(int L,int R,int C,int l,int r,int rt){
if(L <= l && r <= R){
Sum[rt] = C*(r-l+1);
Lazy[rt] = C;
return ;
}
int m=(l+r)>>1;
PushDown(rt,m-l+1,r-m);
if(L <= m) UpdateInterval(L,R,C,l,m,rt<<1);
if(R > m) UpdateInterval(L,R,C,m+1,r,rt<<1|1);
PushUp(rt);
} int Query(int L,int R,int l,int r,int rt){
if(L <= l && r <= R){
return Sum[rt];
}
int m = (l+r)>>1;
PushDown(rt,m-l+1,r-m);
int ANS = 0;
if(L <= m) ANS += Query(L,R,l,m,rt<<1);
if(R > m) ANS += Query(L,R,m+1,r,rt<<1|1);
return ANS;
}
int main()
{
//freopen("in.txt","r",stdin);
while(scanf("%d",&N)!=EOF){
int sum = 0;
Build(0,N-1,1);
for(int i = 0;i<N;++i){
scanf("%d",&x[i]);
sum+= Query(x[i]+1,N-1,0,N-1,1);
UpdatePoint(x[i],0,N-1,1);
}
int ans = sum;
for(int i = 0;i<N;++i){
sum = sum+N-2*x[i]-1;
ans = min(sum,ans);
}
printf("%d\n",ans);
}
return 0;
}

HDU.1394 Minimum Inversion Number (线段树 单点更新 区间求和 逆序对)的更多相关文章

  1. POJ.2299 Ultra-QuickSort (线段树 单点更新 区间求和 逆序对 离散化)

    POJ.2299 Ultra-QuickSort (线段树 单点更新 区间求和 逆序对 离散化) 题意分析 前置技能 线段树求逆序对 离散化 线段树求逆序对已经说过了,具体方法请看这里 离散化 有些数 ...

  2. hdu - 1394 Minimum Inversion Number(线段树水题)

    http://acm.hdu.edu.cn/showproblem.php?pid=1394 很基础的线段树. 先查询在更新,如果后面的数比前面的数小肯定会查询到前面已经更新过的值,这时候返回的sum ...

  3. [HDU] 1394 Minimum Inversion Number [线段树求逆序数]

    Minimum Inversion Number Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java ...

  4. HDU 1394 Minimum Inversion Number(线段树 或 树状数组)

    题目大意:给出从 0 到 n-1 的整数序列,A0,A1,A2...An-1.可将该序列的前m( 0 <= m < n )个数移到后面去,组成其他的序列,例如当 m=2 时,得到序列 A2 ...

  5. HDU 1394 Minimum Inversion Number 线段树

    题目: http://acm.hdu.edu.cn/showproblem.php?pid=1394 没看到多组输入,WA了一万次...... 其实很简单,有人暴力过得,我感觉归并排序.二叉排序树求逆 ...

  6. hdu 1166线段树 单点更新 区间求和

    敌兵布阵 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Submis ...

  7. POJ.3321 Apple Tree ( DFS序 线段树 单点更新 区间求和)

    POJ.3321 Apple Tree ( DFS序 线段树 单点更新 区间求和) 题意分析 卡卡屋前有一株苹果树,每年秋天,树上长了许多苹果.卡卡很喜欢苹果.树上有N个节点,卡卡给他们编号1到N,根 ...

  8. hdu1166(线段树单点更新&区间求和模板)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1166 题意:中文题诶- 思路:线段树单点更新,区间求和模板 代码: #include <iost ...

  9. HDU 1394 Minimum Inversion Number (树状数组)

    题目链接 Problem Description The inversion number of a given number sequence a1, a2, ..., an is the numb ...

随机推荐

  1. mybatis拦截器使用

    目录 mybatis 拦截器接口Interceptor spring boot + mybatis整合 创建自己的拦截器MyInterceptor @Intercepts注解 mybatis拦截器入门 ...

  2. 学习笔记之ubuntu修改固定IP脚本

    一.shell脚本编程 二.正则表达式 三.linux修改IP的方法 #!/bin/bash cd /etc/network/ stty erase '^?' write_interfaces() { ...

  3. 高可用Kubernetes集群-5. 部署flannel网络

    七.部署flannel网络 kubernetes支持基于vxlan方式的flannel与weave网络,基于BGP路由的Calico网络,本节采用flannel网络. Flannel网络采用etcd等 ...

  4. 基于日志报警插件 elastalert 实现告警

    1.官方http://elastalert.readthedocs.io/en/latest/ 2.报警规则示例 http://elastalert.readthedocs.io/en/latest/ ...

  5. LibLas学习笔记

    LibLas学习笔记 las  什么是Las格式 LAS文件格式是数据用户之间交换三维点云数据的公共文件格式. 虽然这种格式主要用于交换激光雷达点云数据,但是它支持交换任何三维的x.y.z 数组. 这 ...

  6. 当Kubernets遇上阿里云 -之七层负载均衡(一).

    我们知道Kubernetes的service只能实现基于4层的负载均衡,无法提供7层之上的许多特性,诸如基于URL的负载均衡,SSL支持,三方授权等等:Ingress可以实现七层负载均衡的许多功能,唯 ...

  7. 使用Node.js 搭建http服务器 http-server 模块

    1. 安装 http-server 模块 npm install http-server -g   全局安装 2.在需要的文件夹   启动 http-server  默认的端口是8080    可以使 ...

  8. P4tutorial实战

    Tutorial样例实战 GitHub仓库地址 参考博客 实验一:SIGCOMM_2015/Sourse_Routing 实验环境: OS:Ubuntu16.04 bmv2:behavioral-mo ...

  9. OC创建对象并访问成员变量

    1.创建一个对象 Car *car =[Car new] 只要用new操作符定义的实体,就会在堆内存中开辟一个新空间 [Car new]在内存中 干了三件事 1)在堆中开辟一段存储空间 2)初始化成员 ...

  10. 解决:Invalid character found in the request target.The valid characters are defined in RFC 7230 and RFC3986

    目录 背景 原因分析 处理方法 参考 背景 在将tomcat升级到7.0.81版后,发现系统的有些功能不能使用了,查询日志发现是有些地址直接被tomcat认为存在不合法字符,返回HTTP 400错误响 ...