问题描述
小明正在整理一批历史文献。这些历史文献中出现了很多日期。小明知道这些日期都在1960年1月1日至2059年12月31日。令小明头疼的是,这些日期采用的格式非常不统一,有采用年/月/日的,有采用月/日/年的,还有采用日/月/年的。更加麻烦的是,年份也都省略了前两位,使得文献上的一个日期,存在很多可能的日期与其对应。
比如02/03/04,可能是2002年03月04日、2004年02月03日或2004年03月02日。
比如02/03/04,可能是2002年03月04日、2004年02月03日或2004年03月02日。
输入格式
一个日期,格式是"AA/BB/CC"。 (0 <= A, B, C <= 9)
输出格式
输出若干个不相同的日期,每个日期一行,格式是"yyyy-MM-dd"。多个日期按从早到晚排列。
样例输入
02/03/04
样例输出
2002-03-04
2004-02-03
2004-03-02
2004-02-03
2004-03-02
思路
这种日期题看到会觉得繁琐麻烦,以后不能这样了,主要就闰年大小月判定这几个步骤,用结构体数组存具体日期。
这个题目有三种存储日期的方式,y/m/r,m/r/y,r/m/y,并且规定要在1960-2059之间,加点小判定就好了,先分别列出来,排序,再去判定符不符合规则即可。
很好的基础题,我也顺便复习了一下运算符的优先级。
这个是87分的代码
#include<bits/stdc++.h>
using namespace std;
struct date{
int y,m,d;
}p[4];///结构体存储
int cmp(struct date a,struct date b){///日期排序
if(a.y!=b.y){
return a.y<b.y;
}
else if(a.m!=b.m){
return a.m<b.m;
}
else return a.d<b.d;
}
bool judge(struct date j){
int c=0;
if(j.y%400==0||j.y%100!=0&&j.y%4==0)c=1;///判断闰年
if(j.m>12||(j.m==1||j.m==3||j.m==5||j.m==7||j.m==8||j.m==10||j.m==12)&&j.d>31)return 0;
if((j.m==4||j.m==6||j.m==9||j.m==11)&&j.d>30)return 0;
if(j.m==2&&j.d>28+c)return 0;
return 1;
}///这个日期判定板子很好
///y,m,r///r,m,y///m,r,y 有这三种方式记录日期
int main()
{
string s;cin>>s;
int a=10*(s[0]-'0')+s[1]-'0';///字符串转整形
int b=10*(s[3]-'0')+s[4]-'0';
int c=10*(s[6]-'0')+s[7]-'0';
if(a>59)p[0].y=1900+a;///题目要求从1960-2059
else p[0].y=2000+a;
p[0].m=b,p[0].d=c;
p[1].m=b,p[1].d=a;
p[2].m=a,p[2].d=b;
if(c>59)p[1].y=p[2].y=1900+c;
else p[1].y=p[2].y=2000+c;
sort(p,p+3,cmp);
for(int i=0;i<3;i++){
if(!judge(p[i])||(p[i].y==p[i+1].y&&p[i].m==p[i+1].m&&p[i].d==p[i+1].d))///符合条件且互不相同
continue;
cout<<p[i].y<<"-";
if(p[i].m<10)cout<<"0"<<p[i].m<<"-";
else cout<<p[i].m<<"-";
if(p[i].d<10)cout<<"0"<<p[i].d<<endl;
else cout<<p[i].d<<endl;
}
}