POJ 2481__Cows

来源:互联网 发布:ubuntu 网卡重启不生效 编辑:程序博客网 时间:2024/06/03 18:23

题目描述:

Farmer John's cows have discovered that the clover growing along the ridge of the hill (which we can think of as a one-dimensional number line) in his field is particularly good. 

Farmer John has N cows (we number the cows from 1 to N). Each of Farmer John's N cows has a range of clover that she particularly likes (these ranges might overlap). The ranges are defined by a closed interval [S,E]. 

But some cows are strong and some are weak. Given two cows: cow i and cow j, their favourite clover range is [Si, Ei] and [Sj, Ej]. If Si <= Sj and Ej <= Ei and Ei - Si > Ej - Sj, we say that cow i is stronger than cow j

For each cow, how many cows are stronger than her? Farmer John needs your help!

题意就是每头牛有一个S值和E值,实际上就是一个[S,E]区间,当这个另一头牛的[S,E]区间能够包含自己的区间时,就认为另一头牛比自己强壮。

输入n表示n头牛,然后输入每头牛的S,E值,n,S,E数据范围都是10的5次方;

输出每头牛的比自己强壮的牛的数目;

样例:

input:

31 20 33 40
output:

1 0 0

对于这道题,我们可以先将所有牛按E从大到下S从小到大来排序,排序完成后就可以发现比当前牛强壮的牛只可能出现在当前牛的前面,那么这个时候就可以用树状数组来完成这道题,用树状数组来储存当前S值之前牛的数目,然后正常更新维护树状数组即可。

AC代码:

#include<iostream>#include<cstdio>#include<cmath>#include<cstring>#include<string>#include<stack>#include<queue>#include<algorithm>using namespace std;const int MAXM=200010;struct cow{    int s;    int e;    int pos;};int n;struct cow c[2*MAXM];int bit[2*MAXM];int cnt[2*MAXM];bool cmp(cow c1,cow c2){    if (c1.e==c2.e)        return c1.s<c2.s;    return c1.e>c2.e;}int lowbit(int x){    return x&(-x);}int sum(int x){    int t=0;    while(x>0)    {        t+=bit[x];        x=x-lowbit(x);    }    return t;}void add(int x){    while(x<2*MAXM)    {        bit[x]++;        x=x+lowbit(x);    }}int main(){    while(scanf("%d",&n)!=EOF)    {        if (n==0) break;        memset(c,0,sizeof(c));        for (int i=1;i<=n;i++)        {            int s,e;            scanf("%d%d",&s,&e);            c[i].s=s;            c[i].e=e;            c[i].pos=i;        }        memset(cnt,0,sizeof(cnt));        memset(bit,0,sizeof(bit));        sort(c+1,c+1+n,cmp);        //for (int i=1;i<=n;i++)            //printf("%d %d \n",c[i].s,c[i].e);        for (int i=1;i<=n;i++)        {            if (c[i].s==c[i-1].s&&c[i].e==c[i-1].e)                cnt[c[i].pos]=cnt[c[i-1].pos];            else            {                cnt[c[i].pos]=sum(c[i].s+1);            }            add(c[i].s+1);        }        for (int i=1;i<=n;i++)        {            if (i==n)                printf("%d\n",cnt[i]);            else                printf("%d ",cnt[i]);        }    }    return 0;}


原创粉丝点击