[hdu3943]K-th Nya Number

  挺正常的一道模板题。

  f[i][j][k]表示i位的数,有j个4,k个7的方案数。

  具体实现的话...我写了发二分答案。。需要注意的是二分时应该是mid=L+(R-L)/2。。不然分分钟爆longlong(unsigned long long党自行退散

  其实也可以从左端点开始慢慢爬。。。但总觉得比较蛋疼所以没敢写

  由网上题解可得,其实还可以确定答案的位数后,从高位往低位一个一个试= =...复杂度会比二分答案的少个log

  需要注意一下对0的特判。。

  对于从左端点爬到根再爬到右端点的奇怪姿势一直不敢碰。。药丸的节奏啊= =。。GDOI应该不会出这么sxbk的东西吧(手动立flag?

 1 #include<cstdio>
 2 #include<iostream>
 3 #include<cstring>
 4 #include<algorithm>
 5 #define ll long long
 6 using namespace std;
 7 struct poi{
 8     ll k;int id;
 9 }q[233];ll ans[233];
10 ll f[20][21][21],ten[20];bool u[20][21][21];
11 int i,j,x,y,X,Y,num;
12 ll l,r,tmp;
13 int s[23],len;
14
15 bool cmp(poi a,poi b){return a.k<b.k;}
16 inline ll get(ll x){
17     for(tmp=x,len=0;tmp;tmp/=10)s[++len]=tmp%10;
18     if(!x)s[len=1]=0;
19     ll ans=0;register int i,j;int sx=X,sy=Y;
20     if(X+Y>len)return 0;
21     for(i=sx+sy;i<len;i++)
22         for(j=1;j<=9;j++)
23             if((sx||j!=4)&&(sy||j!=7))ans+=f[i-1][sx-(j==4)][sy-(j==7)];
24 //    printf("     %lld\n",ans);
25     for(i=1;i<s[len];i++)
26         if((sx||i!=4)&&(sy||i!=7))ans+=f[len-1][sx-(i==4)][sy-(i==7)];
27     sx-=s[len]==4,sy-=s[len]==7;
28     for(i=len-1;i&&sx>=0&&sy>=0;i--){
29         for(j=0;j<s[i];j++)
30             if((sx||j!=4)&&(sy||j!=7))ans+=f[i-1][sx-(j==4)][sy-(j==7)];
31         sx-=s[i]==4,sy-=s[i]==7;
32     }
33     if(!sx&&!sy&&x)ans++;
34 //    printf("     %lld\n",ans);
35     return ans+(!X&&!Y);
36 }
37 int main(){
38     f[1][1][0]=f[1][0][1]=1;f[1][0][0]=8;f[0][0][0]=1;
39     for(i=ten[0]=1;i<=18;i++)ten[i]=ten[i-1]*10;
40     for(i=2;i<=19;i++){
41         for(x=1;x<=i;x++)for(y=i-x;y;y--)
42             f[i][x][y]=x<=y?(f[i-1][x][y]*8+f[i-1][x-1][y]+f[i-1][x][y-1]):f[i][y][x]
43         ;//    ,printf("  %d %d %d   %lld\n",i,x,y,f[i][x][y]);
44         for(x=1;x<=i;x++)f[i][x][0]=f[i][0][x]=f[i-1][x-1][0]+f[i-1][x][0]*8;
45         f[i][0][0]=f[i-1][0][0]<<3;
46     //    if(i<=3)
47     //    for(x=0;x<=i;x++)for(y=0;y<=i-x;y++)printf("  %d %d %d  %lld\n",i,x,y,f[i][x][y]);
48     }
49     int T,TT;scanf("%d",&TT);
50     for(T=1;T<=TT;T++){
51         scanf("%lld%lld%d%d",&l,&r,&X,&Y);scanf("%d",&num);
52         for(i=1;i<=num;i++)scanf("%lld",&q[i].k),q[i].id=i;
53
54         sort(q+1,q+1+num,cmp);
55         ans[0]=l;
56         ll lnum=get(l),mx=get(r)-lnum;
57
58     //    printf("    lnum:%lld   mx:%lld\n",lnum,mx);
59         printf("Case #%d:\n",T);
60         for(i=1;i<=num;i++){
61             ll L=ans[q[i-1].id],R=r,mid;
62             if(q[i].k==q[i-1].k){ans[q[i].id]=L;continue;}
63             if(q[i].k>mx){ans[q[i].id]=-1;continue;}
64             while(L<R){
65                 mid=L+((R-L)>>1);//printf("   %lld %lld  \n",L,R);
66                 if(get(mid)>=q[i].k+lnum)R=mid;else L=mid+1;
67             }//puts("");
68             ans[q[i].id]=L;
69         }
70         for(i=1;i<=num;i++)
71             if(ans[i]==-1)puts("Nya!");else printf("%lld\n",ans[i]);
72     }
73     return 0;
74 }

  话说网上有些题解遇到极限数据会炸>_<。。

时间: 2024-10-28 04:04:56

[hdu3943]K-th Nya Number的相关文章

HDU 3943 K-th Nya Number

K-th Nya Number Time Limit: 1000ms Memory Limit: 65536KB This problem will be judged on HDU. Original ID: 3943 64-bit integer IO format: %I64d      Java class name: Main Arcueid likes nya number very much.A nya number is the number which has exactly

HDU 3943 K-th Nya Number(数位dp+二分)

Problem Description Arcueid likes nya number very much. A nya number is the number which has exactly X fours and Y sevens(If X=2 and Y=3 , 172441277 and 47770142 are nya numbers.But 14777 is not a nya number ,because it has only 1 four). Now, Arcueid

【ACM-ICPC 2018 沈阳赛区网络预赛 K】Supreme Number

[链接] 我是链接,点我呀:) [题意] 在这里输入题意 [题解] 显然每个数字只可能是1,3,5,7 然后如果3,5,7这些数字出现两次以上.显然两个3||5||7都能被11整除. 然后1的话最多能出现两次. 那么也就是说最多只可能有5位数字. 把小于等于5位的全都枚举一遍.求出合法的就好. 如果n>=5位就直接输出那个最大的就Ok. [代码] #include <bits/stdc++.h> #define LL long long #define rep1(i,a,b) for (

POJ2985 The k-th Largest Group[树状数组求第k大值 并查集]

The k-th Largest Group Time Limit: 2000MS   Memory Limit: 131072K Total Submissions: 8807   Accepted: 2875 Description Newman likes playing with cats. He possesses lots of cats in his home. Because the number of cats is really huge, Newman wants to g

Majority Number I &amp; || &amp;&amp; |||

Majority Number Given an array of integers, the majority number is the number that occurs more than half of the size of the array. Find it. Example Given [1, 1, 1, 1, 2, 2, 2], return 1 分析: 既然这里只有一个majority number,那么它的个数减去其它number个数之和还是为正值. 1 public

《数据结构与算法分析:C语言描述》读书笔记------练习1.1 求第K大的数

求一组N个数中的第k个最大者,设k=N/2. 1 import java.util.Random; 2 3 4 public class K_Max { 5 6 /** 7 * @param args 8 */ 9 //求第K大的数,保证K大于等于1,小于等于array.length/2哦 10 public static int TopK(int array[],int K) 11 { 12 int topk[] = new int [K]; 13 for(int i = 0; i<topk.

POJ 2985 The k-th Largest Group(树状数组 并查集/查找第k大的数)

传送门 The k-th Largest Group Time Limit: 2000MS   Memory Limit: 131072K Total Submissions: 8690   Accepted: 2847 Description Newman likes playing with cats. He possesses lots of cats in his home. Because the number of cats is really huge, Newman wants

LintCode-Majority Number III

Given an array of integers and a number k, the majority number is the number that occurs more than 1/k of the size of the array. Find it. Note There is only one majority number in the array. Example For [3,1,2,3,2,3,3,4,4,4] and k = 3, return 3 Chall

Majority Number III

Given an array of integers and a number k, the majority number is the number that occursmore than 1/k of the size of the array. Find it. Example Given [3,1,2,3,2,3,3,4,4,4] and k=3, return 3. Note There is only one majority number in the array. Chall