(线段树)hdoj1394-Minimum Inversion Number 逆序对

The inversion number of a given number sequence a1, a2, ..., an is the number of pairs (ai, aj) that satisfy i < j and ai > aj. 

For a given sequence of numbers a1, a2, ..., an, if we move the first m >= 0 numbers to the end of the seqence, we will obtain another sequence. There are totally n such sequences as the following: 

a1, a2, ..., an-1, an (where m = 0 - the initial seqence) 
a2, a3, ..., an, a1 (where m = 1) 
a3, a4, ..., an, a1, a2 (where m = 2) 
... 
an, a1, a2, ..., an-1 (where m = n-1) 

You are asked to write a program to find the minimum inversion number out of the above sequences. 

InputThe input consists of a number of test cases. Each case consists of two lines: the first line contains a positive integer n (n <= 5000); the next line contains a permutation of the n integers from 0 to n-1.
OutputFor each case, output the minimum inversion number on a single line. 
Sample Input

10
1 3 6 9 0 8 5 7 4 2

Sample Output

16

解题思路:
线段树各个结点记录m——n之间有多少个数已经出现。
 1 #include <iostream>
 2 #include <queue>
 3 #include <cstdio>
 4 #include <cstring>
 5 #include <algorithm>
 6 using namespace std;
 7 typedef long long ll;
 8 typedef unsigned long long ull;
 9 struct node
10 {
11     int left,right,mid;
12     int num;
13 }st[50005];
14 void init(int l,int r,int n)
15 {
16     st[n].left=l;
17     st[n].right=r;
18     st[n].mid=(l+r)/2;
19     st[n].num=0;
20     if(l+1==r)
21         return;
22     init(l,(l+r)/2,2*n);
23     init((l+r)/2,r,2*n+1);
24 }
25 void update(int pri,int n)
26 {
27     st[n].num++;
28     if(st[n].left+1==st[n].right)
29         return;
30     if(pri>=st[n].mid)
31         update(pri,2*n+1);
32     else
33         update(pri,2*n);
34 }
35 int query(int pri,int n)
36 {
37     if(st[n].left+1==st[n].right)
38         return st[n].num;
39     if(pri>=st[n].mid)
40         return query(pri,2*n)+query(pri,2*n+1);
41     else
42         return  query(pri,2*n);
43 
44 }
45 int n;
46 int tem;
47 int an=0;
48 int ans=0;
49 int x[5005];
50 int main()
51 {
52     while(~scanf("%d",&n))
53     {
54         an=0;
55         init(1,n+1,1);
56         int i;
57         for(i=1;i<=n;i++)
58         {
59             scanf("%d",&tem);
60             x[i]=n-tem;
61             an+=query(n-tem,1);
62             update(n-tem,1);
63 //            an+=query(tem+1,1);
64 //            update(tem+1,1);
65 //            printf("i=%d an=%d\n",i,an);
66         }
67         ans=an;
68         for(i=1;i<=n;i++)
69         {
70             ans+=(-n+2*x[i]-1);
71             an=min(ans,an);
72         }
73         printf("%d\n",an);
74     }
75 }

 原先的写的好差啊……居然还不T能过……

 1 #include <iostream>
 2 #include<bits/stdc++.h>
 3 #include <stack>
 4 #include <queue>
 5 #include <map>
 6 #include <set>
 7 #include <cstdio>
 8 #include <cstring>
 9 #include <algorithm>
10 #include <math.h>
11 using namespace std;
12 typedef long long ll;
13 typedef unsigned long long ull;
14 const int MAX=5e3+5;
15 int a[MAX],sum[MAX<<2];
16 int n;
17 void update(int lo,int l,int r,int k)
18 {
19     sum[k]++;
20     if(l==r)
21         return;
22     int mid=l+r>>1;
23     if(lo<=mid)
24         update(lo,l,mid,2*k);
25     else
26         update(lo,mid+1,r,2*k+1);
27 }
28 int query(int left,int l,int r,int k)
29 {
30     if(l>=left)
31         return sum[k];
32     int mid=l+r>>1;
33     if(left>mid)
34         return query(left,mid+1,r,2*k+1);
35     else
36         return query(left,l,mid,2*k)+query(left,mid+1,r,2*k+1);
37 }
38 int an,he;
39 int main()
40 {
41     while(~scanf("%d",&n))
42     {
43         an=0;
44         for(int i=0;i<=n*4;i++)
45             sum[i]=0;
46         for(int i=1;i<=n;i++)
47         {
48             scanf("%d",&a[i]);
49             update(a[i],0,n-1,1);
50             if(a[i]!=n-1)
51                 an+=query(a[i]+1,0,n-1,1);
52         }
53         he=an;
54         for(int i=1;i<n;i++)
55         {
56             he=he+n-1-2*a[i];
57             an=min(an,he);
58         }
59         printf("%d\n",an);
60     }
61 }

 

posted @ 2017-02-13 21:55  perplex  阅读(166)  评论(0编辑  收藏  举报