Ultra-QuickSort POJ 2299(归并排序)
http://acm.hust.edu.cn/vjudge/contest/124435#problem/D
题意:给出一个长度为n的数列,你每一次可以随意交换其中两个数字的位置。问你至少交换几次,才能使得这个数列是个单调递增数列。
比赛时没做出来,(自然,比赛后也没做出来。。。)
找了度娘后,发现有三种方法(线段树, 树状数组, 归并排序),然而我一种也不会。
**************************************************************************************************************************************
下面介绍介绍归并排序:
由于本题实际上就是要求逆序对(即满足i<j,a[i]>a[j]的数对)的个数。而我们再回顾一下归并排序的过程:
假设回溯到某一步,后面的两部分已经排好序(就是说当前需要归并的两个部分都是分别有序的),假设这两个序列为
序列a1:2 3 5 9
序列a2:1 4 6 8
此时我们的目的就是要将a1和a2合并为一个序列。
由于在没排序前a2序列一定全部都是在a1序列之后的,当我们比较a2的1与a1的2时,发现1<2按照归并的思想就会先记录下a2的1,而这里实际上就是对冒泡排序的优化,冒泡是将a2的1依次与a1的9,5,3,2交换就需要4次,而归并却只有一次就完成了,要怎么去记录这个4呢,实际上由于1比2小而2后面还有4个数,也就是说那我的结果就必须要+4,也就是记录a1序列找到第一个比a2某一个大的数,他后面还余下的数的个数就是要交换的次数。
同时我们看a2的4时,a1中第一个比它大的数是5,5之后共有两个数,那结果就+2,。依次下去就可以计算出结果。但是由于我们任然没有改变归并排序的过程。所以复杂度还是O(nlogn)。
#include <stdio.h> #include <string.h> #define maxn 500010 int n, A[maxn], T[maxn]; long long ans;void Merg_Sort(int x, int y) {if(y-x<=1) return ;int mid=x+(y-x)/2;Merg_Sort(x, mid);Merg_Sort(mid, y);int p=x, q=mid, i=x;while(p<mid || q<y){if(q>=y || (p<mid && A[p]<=A[q])) T[i++]=A[p++];else//else的条件是(p==mid || A[q] < A[p]) {if(p<mid) ans+=(mid-p);//由于是p<mid,所以此时也就是相当于 A[q] < A[p]T[i++] = A[q++]; //上面同时A[p]是第一个<A[q]的数,所以+后面还有的数(mid-p) }}for(i=x; i<y; i++)A[i] = T[i]; }int main() {while(scanf("%d", &n),n){memset(A, 0, sizeof(A));memset(T, 0, sizeof(T));for(int i=0; i<n; i++)scanf("%d", &A[i]);ans = 0;Merg_Sort(0, n);printf("%I64d\n", ans);}return 0; }
View Code
转载于:https://www.cnblogs.com/daydayupacm/p/5715324.html
Ultra-QuickSort POJ 2299(归并排序)相关推荐
- 【逆序对】Ultra - Quicksort
POJ 2299 Ultra-QuickSort 只允许交换,比较相邻的元素, 求最少多少次交换可以使得序列有序 冒泡排序的次数-->数列中逆序对的个数减1-->最终为0 -->答案 ...
- poj 2299 Ultra-QuickSort
http://poj.org/problem?id=2299 归并排序 代码: #include<iostream> #include<stdio.h> #include< ...
- POJ 2299 Ultra-QuickSort(线段树+离散化)
题目地址:POJ 2299 这题以前用归并排序做过.线段树加上离散化也能够做.一般线段树的话会超时. 这题的数字最大到10^10次方,显然太大,可是能够利用下标,下标总共仅仅有50w.能够从数字大的開 ...
- POJ - 2299 Ultra-QuickSort(线段树+离散化/归并排序)
题目链接:点击查看 题目大意:给出n个数字,求使用冒泡排序所需要交换的次数 题目分析:这个题n给到了5e5,如果直接冒泡排序的话,的时间复杂度肯定就TLE了,所以不能直接暴力模拟 我们换个思路,这个题 ...
- poj 2299 (归并排序)
给定一个无序的数列,由32位整数组成的,序列长度可达500000,现在通过不断的两两交换,把这个序列排成由小到大的有序序列,问交换的次数是多少. 1 #include<stdio.h> 2 ...
- poj 2299 Ultra-QuickSort(树状数组求逆序数+离散化)
题目链接:http://poj.org/problem?id=2299 Description In this problem, you have to analyze a particular so ...
- POJ 2299 Ultra-QuickSort(树状数组 + 离散)
链接:http://poj.org/problem?id=2299 题意:给出N个数组成的数列A(0 <= A[i] <= 999,999,999),求该数列逆序对的数量. 分析:题目所谓 ...
- zoj 2386 || poj 2299 Ultra-QuickSort
我晕 ,这个我没有写题解么..忘了.. 求逆序数... 白皮书上有,用的归并排序,今天又看了算导的归并排序,写了下,过了. 因为这个题在树状数组的分类下的,所以尝试用树状数组做.想了会... 因为数的 ...
- POJ 2299 Ultra-QuickSort(树状数组+离散化)
题目大意: 就是说,给你一个序列,然后让你求出这个序列有多少个逆序对,所谓逆序对就是对于这个序列中的元素有a[i]>a[j] 且i<j存在. 其实原题是这样说的,给你一个序列,让你用最少的 ...
最新文章
- Windows 8.1 explorer.exe总是崩溃的解决办法
- es6 class extends
- 【渝粤教育】 国家开放大学2020年春季 2772家畜环境卫生与设施 参考试题
- python做数据和大数据区别_不懂Python,不懂大数据的人,和咸鱼有什么区别?
- 2018百度之星程序设计大赛 - 资格赛 1002 子串查询
- (85)FPGA显示激励(monitor)
- 去年购房者平均年龄为29.5岁 80后家庭人均居住面积最小
- Zabbix监控和分布式部署实施方案
- HTML字符实体大全
- 雷林鹏分享:PHP 变量
- WINDOWS10的任务管理器不能自动刷新?
- Javascript: 前端JS生成验证码
- 有趣的c语言代码大全,分享一段有趣的小代码
- 三维计算机软件图,三维cad看图
- 几种将将虚幻引擎内容流送到多个平台的推流方案比较
- DNS服务器的原理及搭建
- 投入Anaconda的怀抱,Anaconda及Jupyter Notebook简介
- 操作系统------虚拟存储器 请求分页存储管理方式
- 03 html基础详解
- Word 设置页码从指定页开始的详细步骤!