- 问题描述
-
In the New Year 2014, Xiao Ming is thinking about the question: give two integers N and K, Calculate the number of the numbers of satisfy the following conditions:
1. It is a positive integer and is not greater than N.
2. Xor value of its all digital is K.
For example N = 12, K = 3, the number of satisfy condition is 3 and 12 (3 = 3, 1 ^ 2 = 3).
In order to let Xiao Ming happy in the New Year 2014, can you help him?
- 输入
-
There are multiple test cases, each test sample contains two positive integers N and K (0 <= N, K < 10 ^ 18), End to file.
- 输出
-
For each case, output the number of the numbers of satisfy condition in one line.
- 样例输入
-
12 3 999 5 12354 8
- 样例输出
-
2 76 662
个位数最大是(1001)2,所以各位的数异或后最大是(1111)2,也就是(15)10,所以k>15的可以直接输出0;
dp[i][j],表示处理到了i位,异或值是j的答案,注意要求的数字>0,所以要加个前导0的判断
注意每次都要初始化dp;
#include <stdio.h>
#include <string.h>
#include <algorithm>
using namespace std;
typedef long long ll;
ll dp[20][20];
ll n,k;
int num[20],len;
inline ll dfs(int i,int Xor,bool e,bool pre){
if(i==-1){
return Xor*1LL==k&&!pre;
}
if(!e && !pre && dp[i][Xor]!=-1) return dp[i][Xor];
int v=(e?num[i]:9);
ll ans=0;
for(int j=0;j<=v;j++){
if(j==0&&pre){
ans+=dfs(i-1,0,0,1);
}
else
ans+=dfs(i-1,Xor^j,e&&(j==v),0);
}
if(!e&&!pre) dp[i][Xor]=ans;
return ans;
}
inline ll solve(ll n){
len=0;
while(n){
num[len++]=n%10;
n/=10;
}
return dfs(len-1,0,1,1);
}
int main(){
while(~scanf("%lld%lld",&n,&k)){
if(k>15||n==0) puts("0");
else{
memset(dp,-1,sizeof(dp));
printf("%lld\n",solve(n));
}
}
}