做法;先化成二进制,当然,这里的dp可以直接用组合数做,因为只有01嘛。POJ 神服务器,把LL 改成int型立马就过了..
#include<cstdio>
#include <iostream>
#define LL int
//23123 132131
const int LMT=40;
using namespace std;
LL c[LMT][LMT],num[LMT];
void init(void)
{
for(int i=0;i<LMT;i++)c[i][0]=c[i][i]=1;
for(int i=1;i<LMT;i++)
for(int j=1;j<i;j++)
c[i][j]=c[i-1][j-1]+c[i-1][j];
}
int leng(LL x)
{
int ret=0;
do
num[ret++]=x&1;
while(x>>=1);
return ret;
}
LL work(LL x)
{
if(x<=1)return 0;
LL res=0;
int n1=0,n0=0,len=leng(x);
for(int i=len-1;i>=0;i--)
if(num[i])n1++;
else n0++;
if(n0>=n1)res++;
for(int i=1;i<len;i++)
for(int j=i-1;j>=0&&j>=i-j;j--)
res+=c[i-1][j];
n0=0;n1=1;
for(int i=len-2;i>=0;i--)
if(num[i])
{
for(int j=i;j+n0+1>=n1+i-j;j--)
res+=c[i][j];
n1++;
}
else n0++;
return res;
}
int main()
{
LL n,m;
init();
cin>>n>>m;
cout<<work(m)-work(n-1)<<endl;
return 0;
}