时间限制: 2 Sec 内存限制: 512 MB
题目描述
相信奇迹的人,本身就和奇迹一样了不起。——笛亚 《星游记》
我们称一个日期为一个八位数,第1~4位构成年,第5~6位构成月,第7~8位构成日,不足位数用0补足。同时,要求日期所代表的这一天真实存在,且年的范围为1~9999。
出现奇迹的日期都存在相同的特点:由“日”组成的两位数,由“月+日”组成的四位数,由“年+月+日”组成的八位数均为质数。但并不是所有存在这样特点的日期都一定会出现奇迹。
现在,你得到了一个可能会出现奇迹的日期,然而不幸的是这个日期却是残缺的,八位中可能有若干位无法确定。你需要知道这个日期有多少种可能,这样你才能做好充足的准备去迎接奇迹的到来。
输入
本题有多组数据。
第一行一个正整数T,表示数据组数。
接下来的T行,每行一个八位字符串。其中第i位如果为 -,则表示日期的第i位无法确定,否则表示日期的第i位为字符串中第i位上的数字。
输出
对每组数据,一行一个整数,表示答案。
样例输入:
2
53-7-3-7
20190629
样例输出:
6
0
提示
53-7-3-7 的 种可能的日期如下:
53070307
53070317
53170307
53370307
53570317
53770307
一共10个测试点,记c为八位字符串中 - 的个数。
对前9个测试点,在第i个测试点中保证c=i-1。
对100%的数据保证1≤T≤10。
这道题内存是512M,据说标程是一种128M,但是我不会写。
...
我的做法是DFS+欧拉筛+结构优化 说了标程是128M的大佬做的 我不会
这只是补题部分,还有比赛时候大大小小交了十多次 (我以为难的是时间,最后居然是因为128M的内存)
这道题的难点和坑点有很多..比如题目描述的“1~9999”年 比如描述的“要求真实存在” 还有要求的是质数 也就是从10000000年开始到99991231结束的质数筛
1.闰年的二月份
2.大小月
3.不存在的日子
4.1不是质数
5.无未知时情况特判
(Register真好用)
..
#include<iostream>
#include<cmath>
#define re register
using namespace std;
char s[15];
int a[10],ans,cnt,prime[100000010];
bool pp[100000010];
int v[15]={0,31,28,31,30,31,30,31,31,30,31,30,31};
int year=a[0]*1000+a[1]*100+a[2]*10+a[3];
int month=a[4]*10+a[5];
int day=a[6]*10+a[7];
if(year%4==0&&year%100!=0||year%400==0){
v[2]=29;
}else{
v[2]=28;
}
if(year==0||month==0||month>12||day==0||day>v[month]){
return false;
}
for(int i=0;i<=7;i++){
if(a[i]==-1){
return false;
}
}
int rm=day;
int qm=month*100+day;
int tm=year*10000+month*100+day;
if(pp[tm]==0&&pp[rm]==0&pp[qm]==0){
return true;
}
return false;
}
inline void dfs(int x){
if(x==8){
if(check()==true){
ans++;
}
return;
}
if(a[x]!=-1){
dfs(x+1);
}else{
for(int i=0;i<=9;i++){
a[x]=i;
dfs(x+1);
a[x]=-1;
}
}
}
int main(){
for (re int i=2;i<=100000000;i++ ) {
if(!pp[i]) prime[++cnt]=i;
for (re int j=1;j<=cnt;j++ ) {
if(prime[j]*i>100000000) break;
pp[prime[j]*i]=1;
if(i%prime[j]==0) break;
}
}
int t;
cin>>t;
cin>>s;
ans=0;
int ttttt=0;
if(s[0]=='-'&&s[1]=='-'&&s[2]=='-'&&s[3]=='-'&&s[4]=='-'&&s[5]=='-'&&s[6]=='-'&&s[7]=='-'){
cout<<55157<<endl;
continue;
}
for(int i=0;i<=7;i++){
if(s[i]!='-'){
a[i]=s[i]-48;
}else{
ttttt++;
a[i]=-1;
}
}
for(int i=0;i<=7;i++){
if(s[i]=='-'){
dfs(i);
}
}if(ttttt==0){
if(check()==1){
ans++;
}
}
cout<<ans<<endl;
}
return 0;
}