归并排序刷题

POJ 2299 超快速排序

两两交换生成有序序列  ----》 数逆序元素的个数  逆序对

mid-i+1 第一个元素的下标 i 

子序列之后要有序

在合并的时候数一数逆序对的个数 

110 = 6     6/2 = 3    右移一位 011=3  左移动 1100=12

 1 #include <iostream>
 2 #include <cstdio>
 3 #include <cstring>
 4 using namespace std;
 5 const int maxn=500010;
 6 int a[maxn], b[maxn];
 7 // 不用动态的分配空间 开辟静态数组50个数组或者1w的时间差距并不大,动态数组时间差距比较大。频繁的开辟动态数组会影响算法的效率
 8 long long cnt;
 9 
10 void Merge(int low, int mid, int high){
11     int i=low, j=mid+1, k=low;
12     while (i<=mid && j<=high) {  // 按照从小到大存放到辅助书B[]中
13         if(a[i]<=a[j])
14             b[k++] = a[i++];
15         else{
16             b[k++] = a[j++];
17             cnt += (long long)(mid-i+1);
18         }
19     }
20     while(i<=mid) b[k++]=a[i++];
21     while(j<=high) b[k++]=a[j++];
22     for(k=low; k<=high; k++)
23         a[k] = b[k];
24 }
25 
26 void MergeSort(int low, int high){
27     if(low<high){
28         int mid = (low + high) >> 1;  //右移操作比除法快
29         // 分数组
30         MergeSort(low, mid);
31         MergeSort(mid+1, high);
32         // 合并
33         Merge(low, mid, high);
34     }
35 }
36 int main(){
37     int n;
38     while (scanf("%d", &n) && n) {
39         cnt = 0;
40         for(int i=0; i<n; i++)
41             scanf("%d", &a[i]);
42         MergeSort(0, n-1);
43         printf("%lld\n", cnt);  // %I64d 杭电不让用lld可以使用%I64d代替
44     }
45     return 0;
46 }

HDU 1031

https://vjudge.net/problem/HDU-1031

对满意度之和排序递减排序(从大到小),满意度相等按id递增(从小到大),取前k个,按照缩影递减输出(从大到小),输出的是索引。

 1 #include <iostream>
 2 #include <cstdio>
 3 #include <algorithm>
 4 
 5 using namespace std;
 6 
 7 struct data{
 8     int id;
 9     double value;
10 }a[10010];
11 
12 void Merge(data A[], int low, int mid, int high, bool flag){  // 合并函数
13     data *B= new data[high-low+1];  // 辅助数组
14     int i=low, j=mid+1, k=0;
15     double x, y;
16     // 按照满意度递减、按照索引递减 用flag区别
17     while (i<=mid && j<=high) {
18         
19         if(!flag){
20             x = A[i].value;
21             y = A[j].value;
22         }else{
23             x = A[i].id;
24             y = A[j].id;
25         }
26         
27         if(x>=y)  // 保证了id小的在前
28             B[k++] = A[i++];
29         else
30             B[k++] = A[j++];
31     }
32     while(i<=mid) B[k++]=A[i++];
33     while(j<=high) B[k++]=A[j++];
34     for(i=low, k=0; i<=high; i++, k++)
35         A[i] = B[k];
36     delete []B;
37 }
38 
39 void MergeSort(data A[], int low, int high, bool flag){
40     if(low < high){
41         int mid = (low+high)>>1;
42         MergeSort(A, low, mid, flag);
43         MergeSort(A, mid+1, high, flag);
44         Merge(A, low, mid, high, flag);
45     }
46 }
47 
48 int main(){
49     int n, m, k;
50     double x;
51     while (scanf("%d%d%d", &n, &m, &k)!=EOF) {
52         for(int i=0; i<m; i++){
53             a[i].id = i+1;
54             a[i].value = 0.0;
55         }
56         for(int i=0; i<n; i++){
57             for(int j=0; j<m; j++){
58                 scanf("%lf", &x);
59                 a[j].value += x;
60             }
61         }
62         MergeSort(a, 0, m-1, 0);  // 按值非递增
63         MergeSort(a, 0, k-1, 1);  // 按序号非递增 我们只要钱前k个
64         for(int i=0; i<k-1; i++)
65             printf("%d ", a[i].id);
66         printf("%d\n", a[k-1].id);
67     }
68     return 0;
69 }
 1 #include <iostream>
 2 #include <cstdio>
 3 #include <algorithm>
 4 
 5 using namespace std;
 6 
 7 struct data{
 8     int id;
 9     double value;
10 }a[10010];
11 
12 bool cmp1(data a, data b){
13     if(a.value == b.value)
14         return a.id < b.id;
15     return a.value>b.value;
16 }
17 
18 bool cmp2(data a, data b){
19     return a.id > b.id;
20 }
21 
22 int main(){
23     int n, m, k;
24     double x;
25     while (scanf("%d%d%d", &n, &m, &k)!=EOF) {
26         for(int i=0; i<m; i++){
27             a[i].id = i+1;
28             a[i].value = 0.0;
29         }
30         for(int i=0; i<n; i++){
31             for(int j=0; j<m; j++){
32                 scanf("%lf", &x);
33                 a[j].value += x;
34             }
35         }
36         sort(a, a+m, cmp1);  // 按值降序
37         sort(a, a+k, cmp2);  // 按序号降序
38         for(int i=0; i<k-1; i++)
39             printf("%d ", a[i].id);
40         printf("%d\n", a[k-1].id);
41     }
42     return 0;
43 }

猜你喜欢

转载自www.cnblogs.com/JCcodeblgos/p/11452151.html
今日推荐