现在的位置: 首页 > 综合 > 正文

hdu4588前缀 分区间计算

2013年04月02日 ⁄ 综合 ⁄ 共 688字 ⁄ 字号 评论关闭

这题和上次做的Uva11361和相似,也是区间查询,利用前缀数组来存,结果为a[r]-a[l-1]。

这题注意转化为求每一位的1的个数和。

做题时遇到一个小的问题,(0<<1)=0,调试了好久,以后得注意了。

代码:

#include<iostream>
#include<cstdio>
#include<cmath>
#include<cstring>
#define ll __int64
using namespace std;
void fun(int x,ll *a)
{
    if(x<=0)
    {
        return ;
    }
    int d=0,tx=x;
    while(tx)
    {
        tx/=2;
        d++;
    }
    for(int i=d; i>=1; i--)
    {
        if(i==1)
        {
            if(x&1)
                a[i]+=1;
            continue;
        }
        if(x&((int)(pow(2.0,i-1))))
        {
            a[i]+=(1+x%((int)pow(2.0,i-1)));
            for(int j=i-1; j>=1; j--)
            {
                a[j]+=pow(2,i-2);
            }
            x-=(int)pow(2.0,i-1);
        }
    }
}

int main()
{
    int l,r;
    ll x[66];
    ll y[66];
    while(scanf("%d%d",&l,&r)!=EOF)
    {
        memset(x,0,sizeof(x));
        memset(y,0,sizeof(y));
        fun(l-1,x);
        fun(r,y);
        ll sum=0,tmp=0,a;
        for(int i=1; i<64; i++)
        {
            a=y[i]-x[i];
            tmp=(tmp+a)/2;
            sum+=tmp;
        }
        printf("%I64d\n",sum);
    }
    return 0;
}

抱歉!评论已关闭.