hdu1394 Minimum Inversion Number 单点更新

2024-06-12 11:58

本文主要是介绍hdu1394 Minimum Inversion Number 单点更新,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!


本题虽归于线段树,但实际上只是求逆序数时使用线段树,后面求最小逆序数时并不需要线段树。
首先题目有两个要点:
1.求出原序列的逆序数
2.求出n次移动第一个位置数到最后的逆序数。


对于第一个要点,实际上用暴力也可以解决,当然最好转到线段树的概念上来。

以下我就引用一下别人的话好了。

/ *

先以区间[0,9]为根节点建立val都为0的线段树,  
再看看怎样求下面序列的逆序数: 
1 3 6 9 0 8 5 7 4 2 
在线段树中插入1, 插入之前先询问区间[1,9]已插入的节点数(如果存在,必与1构成逆序)  v1=0 
在线段树中插入3, 插入之前先询问区间[3,9]已插入的节点数(如果存在,必与3构成逆序)  v2=0 
在线段树中插入6, 插入之前先询问区间[6,9]已插入的节点数(如果存在,必与6构成逆序)  v3=0 
在线段树中插入9, 插入之前先询问区间[9,9]已插入的节点数(如果存在,必与9构成逆序)  v4=0 
在线段树中插入0, 插入之前先询问区间[0,9]已插入的节点数(如果存在,必与0构成逆序)  v5=4 
在线段树中插入8, 插入之前先询问区间[8,9]已插入的节点数(如果存在,必与8构成逆序)  v6=1 
在线段树中插入5, 插入之前先询问区间[5,9]已插入的节点数(如果存在,必与5构成逆序)  v7=3 
在线段树中插入7, 插入之前先询问区间[7,9]已插入的节点数(如果存在,必与7构成逆序)  v8=2 
在线段树中插入4, 插入之前先询问区间[4,9]已插入的节点数(如果存在,必与4构成逆序)  v9=5 
在线段树中插入2, 插入之前先询问区间[2,9]已插入的节点数(如果存在,必与2构成逆序)  v10=7 

累加v1+……+v10  =22,这就是1 3 6 9 0 8 5 7 4 2的逆序数了.

*/ 

第二点:
由于数字0~n-1都是连续的,那么我每次把第一个数字移到最后。
例如,我第一个位置的数字是3,那么移动后。
原本不是逆序数对就变成了逆序数对;
原本是逆序数对的就变成了非逆序数对。


所增加的逆序数对 = n-3-1;
所减少的逆序数对 = 3;

这样基本就不难理解了~

以下放出AC代码:

#include <cstdlib>
#include <cstring>
#include <cstdio>
#include <iostream>
#define lson l,mid,rt<<1
#define rson mid+1,r,rt<<1|1
#define min(a,b) a<b?a:b
using namespace std;
const int p = 5005;
int sum [ p<<2 ],cot,a[p];
void build (int l ,int r ,int rt)
{sum[rt]=0;if(l==r)return;int mid = (l + r) >> 1;build(lson);build (rson);
}void query(int l ,int r ,int rt, int x,int y)
{if(x<=l&&r<=y){cot+=sum[rt];return;}int mid = (l + r) >> 1;if(x<=mid)  query(lson,x,y);if(y>mid)  query(rson,x,y);
}void update(int l ,int r ,int rt,int num)
{if(l == r){sum[rt]=1;return;}int mid = (l + r)>>1;if(num<=mid) update(lson,num);if(num>mid) update(rson,num);sum[ rt ]=sum[ rt<<1 ]+sum[ rt<<1|1 ];
}
int main()
{int N,temp;while(scanf("%d",&N)!=EOF){build(0,N-1,1);cot=0;for(int i=1;i<=N;i++){scanf("%d",&a[i]);query(0,N-1,1,a[i],N-1);update(0,N-1,1,a[i]);}int minn=cot;for(int i=1;i<=N;i++){cot = cot - a[i] + N - a[i] - 1 ;minn = min(minn,cot);}printf("%d\n",minn);}return 0;
}



这篇关于hdu1394 Minimum Inversion Number 单点更新的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/1054150

相关文章

Security OAuth2 单点登录流程

单点登录(英语:Single sign-on,缩写为 SSO),又译为单一签入,一种对于许多相互关连,但是又是各自独立的软件系统,提供访问控制的属性。当拥有这项属性时,当用户登录时,就可以获取所有系统的访问权限,不用对每个单一系统都逐一登录。这项功能通常是以轻型目录访问协议(LDAP)来实现,在服务器上会将用户信息存储到LDAP数据库中。相同的,单一注销(single sign-off)就是指

poj3468(线段树成段更新模板题)

题意:包括两个操作:1、将[a.b]上的数字加上v;2、查询区间[a,b]上的和 下面的介绍是下解题思路: 首先介绍  lazy-tag思想:用一个变量记录每一个线段树节点的变化值,当这部分线段的一致性被破坏我们就将这个变化值传递给子区间,大大增加了线段树的效率。 比如现在需要对[a,b]区间值进行加c操作,那么就从根节点[1,n]开始调用update函数进行操作,如果刚好执行到一个子节点,

hdu1394(线段树点更新的应用)

题意:求一个序列经过一定的操作得到的序列的最小逆序数 这题会用到逆序数的一个性质,在0到n-1这些数字组成的乱序排列,将第一个数字A移到最后一位,得到的逆序数为res-a+(n-a-1) 知道上面的知识点后,可以用暴力来解 代码如下: #include<iostream>#include<algorithm>#include<cstring>#include<stack>#in

hdu1689(线段树成段更新)

两种操作:1、set区间[a,b]上数字为v;2、查询[ 1 , n ]上的sum 代码如下: #include<iostream>#include<algorithm>#include<cstring>#include<stack>#include<queue>#include<set>#include<map>#include<stdio.h>#include<stdl

usaco 1.2 Name That Number(数字字母转化)

巧妙的利用code[b[0]-'A'] 将字符ABC...Z转换为数字 需要注意的是重新开一个数组 c [ ] 存储字符串 应人为的在末尾附上 ‘ \ 0 ’ 详见代码: /*ID: who jayLANG: C++TASK: namenum*/#include<stdio.h>#include<string.h>int main(){FILE *fin = fopen (

hdu 1754 I Hate It(线段树,单点更新,区间最值)

题意是求一个线段中的最大数。 线段树的模板题,试用了一下交大的模板。效率有点略低。 代码: #include <stdio.h>#include <string.h>#define TREE_SIZE (1 << (20))//const int TREE_SIZE = 200000 + 10;int max(int a, int b){return a > b ? a :

AI行业应用(不定期更新)

ChatPDF 可以让你上传一个 PDF 文件,然后针对这个 PDF 进行小结和提问。你可以把各种各样你要研究的分析报告交给它,快速获取到想要知道的信息。https://www.chatpdf.com/

GIS图形库更新2024.8.4-9.9

更多精彩内容请访问 dt.sim3d.cn ,关注公众号【sky的数孪技术】,技术交流、源码下载请添加微信:digital_twin123 Cesium 本期发布了1.121 版本。重大新闻,Cesium被Bentley收购。 ✨ 功能和改进 默认启用 MSAA,采样 4 次。若要关闭 MSAA,则可以设置scene.msaaSamples = 1。但是通过比较,发现并没有多大改善。

JavaFX应用更新检测功能(在线自动更新方案)

JavaFX开发的桌面应用属于C端,一般来说需要版本检测和自动更新功能,这里记录一下一种版本检测和自动更新的方法。 1. 整体方案 JavaFX.应用版本检测、自动更新主要涉及一下步骤: 读取本地应用版本拉取远程版本并比较两个版本如果需要升级,那么拉取更新历史弹出升级控制窗口用户选择升级时,拉取升级包解压,重启应用用户选择忽略时,本地版本标志为忽略版本用户选择取消时,隐藏升级控制窗口 2.

题目1380:lucky number

题目1380:lucky number 时间限制:3 秒 内存限制:3 兆 特殊判题:否 提交:2839 解决:300 题目描述: 每个人有自己的lucky number,小A也一样。不过他的lucky number定义不一样。他认为一个序列中某些数出现的次数为n的话,都是他的lucky number。但是,现在这个序列很大,他无法快速找到所有lucky number。既然