您的位置:首页 > 其它

2018年全国多校算法寒假训练营练习比赛(第五场)A 逆序数

2018-02-26 08:53 344 查看
链接:https://www.nowcoder.com/acm/contest/77/A
来源:牛客网

题目描述

在一个排列中,如果一对数的前后位置与大小顺序相反,即前面的数大于后面的数,那么它们就称为一个逆序。一个排列中逆序的总数就称为这个排列的逆序数。比如一个序列为4 5 1 3 2, 那么这个序列的逆序数为7,逆序对分别为(4, 1), (4, 3), (4, 2), (5, 1), (5, 3), (5, 2),(3, 2)。

输入描述:

第一行有一个整数n(1 <= n <= 100000),  然后第二行跟着n个整数,对于第i个数a[i],(0 <= a[i] <= 100000)。

输出描述:

输出这个序列中的逆序数
#include<bits/stdc++.h>
using namespace std;
const int maxn=1e5+7;
int a[maxn];
long long sum(int i)
{
long long ans=0;
while(i>0)
{
ans+=a[i];
i-=i&-i;
}
return ans;
}
void add(int i)
{
while(i<=100000)
{
a[i]+=1;
i+=i&-i;
}
}
int main()
{
int n,i,j;
memset(a,0,sizeof(a));
scanf("%d",&n);
long long ans=0;
for(i=1;i<=n;i++)
{
int x;scanf("%d",&x);
if(x!=0)ans+=sum(100000)-sum(x);
//若非0,求此前的逆序数
else
{
ans+=(long long)(i-1-a[0]);
a[0]++;
//若为0,则此前的非0都是逆序数
}
if(x!=0) add(x);
}
printf("%lld\n",ans);
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐