2017年蓝桥杯C/C++程序设计B组-日期问题

欢迎大家来到zz菜鸟的博客,近期我在备战蓝桥杯,会发布一些我对部分题目的看法。希望大家能够多多支持。

题目描述

小明正在整理一批历史文献。这些历史文献中出现了很多日期。小明知道这些日期都在 1960 年 1 月 1 日至 2059 年 12 月 31 日。令小明头疼的是,这些日期采用的格式非常不统一,有采用年/月/日的,有采用月/日/年的,还有采用日/月/年的。

更加麻烦的是,年份也都省略了前两位,使得文献上的一个日期,存在很多可能的日期与其对应。

比如 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

思路分析

  • 数据类型的转换: 首先注意到这里输入和输出格式都是字符串,而在把输入的字符串中给出的数字信息转化成整数型提起出来,最后输出的时候在转化成字符串型。
  • 日期的处理:由于闰年和平年二月份天数不同,需要对二月单独处理,而要对日期是否规范进行检验。
  • 多个日期排序:由于要多多个日期进行排序且不能重复,故需要用到set容器。

代码

#include<iostream>
#include<sstream>
#include<set>
using namespace std;
bool isleap(int& year)   //判断是否为闰年
{         
	return (year % 4 == 0 && year % 100 != 0) || year % 400 == 0;
}
void i2s(int a, string& y)   //整数转字符串
 {
	stringstream ss;
	ss << a;
	ss>>y;
}
string ff(int a, int b, int c)   //检验日期是否规范并返回输出结果之一
 {
	if (a >= 0 && a <= 59)a += 2000;
	else if (a >= 60 && a <= 99)a += 1900;
	else return"";
	if (b < 1 || b>12)return"";
	if (c < 1 || c>31)return"";
	bool leap = isleap(a);
	switch (b) {
	case 2:
		if (leap && c > 29) return"";
		if (!leap && c > 28) return"";
		break;
	case 4:
		if (c > 30) return"";
		break;
	case 6:
		if (c > 30) return"";
		break;
	case 9:
		if (c > 30) return"";
		break;
	case 11:
		if (c > 30) return"";
		break;
	}
	string y, m, d;
	i2s(a, y);
	i2s(b, m);
	i2s(c, d);
	if (m.length() == 1) m = '0' + m;
	if (d.length() == 1) d = '0' + d;
	return y + '-' + m + '-' + d;
}
int main()
{
	string in;
	cin >> in;
	int a, b, c;   
	// 将字符转化成整数形式
	a = (in[0] - '0') * 10 + (in[1] - '0');
	b = (in[3] - '0') * 10 + (in[4] - '0');
	c = (in[6] - '0') * 10 + (in[7] - '0');
	//得到三种不同的字符串日期
	string case1=ff(a,b,c);
	string case2=ff(c,b,a);
	string case3=ff(c,a,b);
	//使用set容器进行排序和去重
	set<string>ans;    
	if(case1!="")ans.insert(case1);
	if(case2!="")ans.insert(case2);
	if(case3!="")ans.insert(case3);
	for (set<string>::iterator iter = ans.begin(); iter != ans.end(); iter++) {
		cout << *iter << endl;
	}
	return 0;
}
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值