POJ 1990 MooFest 题解 《挑战程序设计竞赛》

来源:互联网 发布:练字软件app 编辑:程序博客网 时间:2024/05/22 18:23
#include <iostream>#include<cstdio>#include<algorithm>using namespace std;typedef long long ll;const int MAX=20005;int n;pair<int,int> cow[MAX];ll num[MAX],dis[MAX];ll sum(ll *bit,int i){    ll s=0;    while(i>0)    {        s+=bit[i];        i-=i&(-i);    }    return s;}ll sum(ll *bit,int from,int to){    return sum(bit,to-1)-sum(bit,from-1);}void add(ll *bit,int i,ll x){    while(i<=MAX)    {        bit[i]+=x;        i+=i&(-i);    }}int main(){    while(cin>>n)    {        for(int i=0;i<n;i++)        cin>>cow[i].first>>cow[i].second;        sort(cow,cow+n);        ll res=0;        for(int i=0;i<n;i++)        {            int h=cow[i].first,x=cow[i].second;             ll left=sum(num,1,x),right=i-left;            res+=h*((left*x-sum(dis,1,x))+(sum(dis,x+1,MAX)-right*x));            add(num,x,1);            add(dis,x,x);        }        cout<<res<<endl;    }    return 0;}

好久未做线段树之类的题了,感觉生疏了许多,参考了一下别人的代码。

首先这一题使用了两个BIT,一个用来求左右两边的cow的个数,另外一个是用来记录所有点到原点的距离之和。

此外,此题先通过听力好坏程度排序,这样每次新更新的牛都是耳背的,不用再比较两个cow的的听力值了。


0 0
原创粉丝点击