HDU_2689_Sort it

其实,这道题暴力也行,两个for就搞定了,时间复杂度为O(N^2),而树状数组的时间复杂度为O(N*logN)。

树状数组求逆序对的原理:

前面有i-1个数,把每次输入的数看作树状数组的下标,设置增加的变量为1,算其前缀和(有多少个1就有多少个顺序对),然后减去顺序对就是答案,方案有两种(本质是一样的):

1、

ans+=(i-1-sum(a));

add(a);

2、

add(a);
ans+=(i-sum(a));

#include<iostream>

#include<cstdio>

#include<cstring>

#include<cmath>

#include<algorithm>

#include<string>

#include<queue>

using namespace std;

#define N 1005

int c[N];

int sum(int x)

{

    int ret=0;

    while(x)

    {

        ret+=c[x];

        x-=(x&-x);

    }

    return ret;

}

void add(int x)

{

    while(x<=N)

    {

        c[x]++;

        x+=(x&-x);

    }

}

int main()

{

    int t,a,ans;

    while(~scanf("%d",&t))

    {

        memset(c,0,sizeof(c));

        ans=0;

        for(int i=1;i<=t;++i)

        {

            scanf("%d",&a);

            add(a); 

            ans+=(i-sum(a));

        }

        printf("%d\n",ans);

    }

    return 0;

}

 

你可能感兴趣的:(sort)