F(x)
Time Limit: 1000/500 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 3567 Accepted Submission(s): 1330
Total Submission(s): 3567 Accepted Submission(s): 1330
Problem Description
For a decimal number x with n digits (A
nA
n-1A
n-2 ... A
2A
1), we define its weight as F(x) = A
n * 2
n-1 + A
n-1 * 2
n-2 + ... + A
2 * 2 + A
1 * 1. Now you are given two numbers A and B, please calculate how many numbers are there between 0 and B, inclusive, whose weight is no more than F(A).
Input
The first line has a number T (T <= 10000) , indicating the number of test cases.
For each test case, there are two numbers A and B (0 <= A,B < 10 9)
For each test case, there are two numbers A and B (0 <= A,B < 10 9)
Output
For every case,you should output "Case #t: " at first, without quotes. The
t is the case number starting from 1. Then output the answer.
Sample Input
3 0 100 1 10 5 100
Sample Output
Case #1: 1 Case #2: 2 Case #3: 13
Source
Recommend
liuyiding | We have carefully selected several similar problems for you:
5717
5716
5715
5714
5713
题目意思:
数i在0~B的范围内,求F(i)小于F(A)的个数。
解题思路:
数位DP。
dp[i][j]表示i位数,F值小于等于j的数的个数。
注意边界的各种情况的判断。
题目意思:
数i在0~B的范围内,求F(i)小于F(A)的个数。
解题思路:
数位DP。
dp[i][j]表示i位数,F值小于等于j的数的个数。
注意边界的各种情况的判断。
#include<cstdio>
#include<cstring>
#include<cmath>
#include<set>
#include<cstdlib>
#include<iostream>
#include<algorithm>
using namespace std;
#define MAXN 100010
int a,b;
int data[22];
int dp[22][20000];//dp[i][j]表示i位数,F值小于等于j的数的个数
int dfs(int pos,int num,int flag)
{
if(pos==-1) return num>=0;
if(num<0) return 0;
if(!flag&&dp[pos][num]>=0) return dp[pos][num];
int res=0,u=flag?data[pos]:9;
for(int i=0; i<=u; ++i)
res+=dfs(pos-1,num-i*(1<<pos),flag&&i==u);//dp[i][j]+=dp[i-1][j-k*(1<<(i-1))]
if(!flag) dp[pos][num]=res;
return res;
}
int doit()//分离数的各个位
{
int al=0,res=0,bl=0;
while(b)
{
data[bl++]=b%10;
b/=10;
}
while(a)
{
res+=(a%10)*(1<<al);//2^al
al++;
a/=10;
}
return dfs(bl-1,res,true);
}
int main()
{
ios::sync_with_stdio(false);
int t,cnt=0;
cin>>t;
memset(dp,-1,sizeof(dp));
while(t--)
{
cin>>a>>b;
cout<<"Case #"<<++cnt<<": "<<doit()<<endl;
}
return 0;
}
/*
3
0 100
1 10
5 100
*/