Another hobby of xhxj is yy(speculation) some magical problems to discover the special properties. For example, when she see a number, she would think whether the digits of a number are strictly increasing. If you consider the number as a string and can get a longest strictly increasing subsequence the length of which is equal to k, the power of this number is k.. It is very simple to determine a single number’s power, but is it also easy to solve this problem with the numbers within an interval? xhxj has a little tired,she want a god cattle to help her solve this problem,the problem is: Determine how many numbers have the power value k in [L,R] in O(1)time.
For the first one to solve this problem,xhxj will upgrade 20 favorability rate。
Input
First a integer T(T<=10000),then T lines follow, every line has three positive integer L,R,K.(
0<L<=R<2 63-1 and 1<=K<=10).
Output
For each query, print "Case #t: ans" in a line, in which t is the number of the test case starting from 1 and ans is the answer.
Sample Input
1 123 321 2
Sample Output
Case #1: 139
#include <bits/stdc++.h>
using namespace std;
int K;
bool flag;
int ch[30];
long long dp[20][1500][10];
int lis[1500], nx[1500][10];
// LIS 最长上升子序列
int nextt(int sum, int t)
{
int pos = -1;
for (int i = t; i < 10; i++)
if (sum >> i & 1)
{
pos = i; // 找到第一个大于i的数
break;
}
if (pos != -1) // 找不到 加上对应位的二进制(接在原序列后) 找到则修改
sum -= (1 << pos);
sum += (1 << t);
return sum;
}
void init()
{
memset(dp, -1, sizeof dp);
/// 状态压缩 用二进制数代表模拟的上升序列数组 1的个数即上升序列长度
for (int i = 0; i < 1024; i++)
{
lis[i] = 0;
for (int j = 0; j < 10; j++)
if (i >> j & 1)
lis[i]++;
}
/// 当前i代表的序列情况下 下一个字符为j的变更情况
for (int i = 0; i < 1024; i++)
{
for (int j = 0; j < 10; j++)
nx[i][j] = nextt(i, j);
}
}
long long dfs(int pos, int sum, bool lim)
{
if (pos == 0)
return (lis[sum] == K) ? 1 : 0;
if (!lim && dp[pos][sum][K] != -1)
return dp[pos][sum][K];
long long res = 0;
int up = lim ? ch[pos] : 9;
for (int i = 0; i <= up; i++)
res += dfs(pos - 1, (!sum && !i) ? 0 : nx[sum][i], lim && (i == up));
if (!lim) /// K不同答案不同
dp[pos][sum][K] = res;
return res;
}
long long solve(long long x)
{
int w = 0;
while (x)
{
ch[++w] = x % 10;
x /= 10;
}
return dfs(w, 0, 1);
}
int main()
{
//freopen("D:\\in.txt", "r", stdin);
int t;
scanf("%d", &t);
init();
for (int i = 1; i <= t; i++)
{
long long a, b;
scanf("%lld %lld %d", &a, &b, &K);
printf("Case #%d: %lld\n", i, solve(b) - solve(a - 1));
}
return 0;
}