题意:
给你N个排列不规则的数,任务是把它从小到大排好,
每次只能交换相邻两个数,交换一次的代价为两数之和,求最小代价注意 :每次交换 都必须只能交换相邻的2个
来自这里
解法:
<树状数组>
策略:先交换前
i
个数使其有序,再处理第
处理第
i
个数
->
cost(i)=k1∗ai+k2
k1=total[(bool)(aj>ai)]
k2=total[aj]
用树状数组实现是极好的~
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#define MAXN 100005
int n;
long long b[MAXN]={0},c[MAXN]={0};
long long ans=0;
int lowbit(int x)
{
return x&(-x);
}
void add(int s,int c,long long *x)
{
while(s<=n)
{
x[s]+=c;
s+=lowbit(s);
}
}
long long count(int s,long long *x)
{
long long ret=0;
while(s>0)
{
ret+=x[s];
s-=lowbit(s);
}
return ret;
}
int main()
{
int i,j,T;int ai;
#ifndef ONLINE_JUDGE
freopen("hdu2838.in","r",stdin);
freopen("hdu2838.out","w",stdout);
#endif
scanf("%d",&n);
for(i=1;i<=n;i++)
{
scanf("%d",&ai);
ans+=(count(n,b)-count(ai,b))*ai+(count(n,c)-count(ai,c));
add(ai,1,b);
add(ai,ai,c);
}
printf("%I64d\n",ans);
#ifndef ONLINE_JUDGE
fclose(stdin);
fclose(stdout);
#endif
return 0;
}