简介:
A(n)表示n的二进制中有多少个“11”出现
计算A(0)+A(1)+…+A(n)
分析:
一眼看出递推式:
A(n)=A(n/2)+(n/2和n都是奇数 ? 1:0)
这个式子算A(n)是很简单啦,但是求前缀和我就GG了
这道题实际和 UVA 11038 这题类似,枚举中间,然后处理两边的情况。
不过本题最大的答案会超过ll,要用高精度,不过借鉴大佬的方法,直接用两个数字来保存一个数字,这样能保存到2个ll的长度,就足够存放答案了
tip
说实话我不大懂这道题
//这里写代码片
#include<cstdio>
#include<cstring>
#include<iostream>
#define ll long long
using namespace std;
const ll M=1e13;
ll n,p,q;
void add(ll x)
{
q+=x;
p+=q/M;
q%=M;
}
void solve()
{
p=q=0;
ll a=n,b=1;
while (n>1)
{
add((n>>2)*b);
if ((n&3)==3)
add((a&(b-1))+1);
b<<=1;
n>>=1;
}
if (p)
{
printf("%lld",p);
printf("%013lld\n",q);
}
else
printf("%lld\n",q);
}
int main()
{
int cas=0;
while (scanf("%lld",&n)!=EOF&&n>=0)
{
printf("Case %d: ",++cas);
solve();
}
return 0;
}