这是《C++算法宝典》算法篇的第09节文章啦~
如果你之前没有太多C++基础,请点击👉专栏:C++语法入门,如果你C++语法基础已经炉火纯青,则可以进阶算法👉专栏:算法知识和数据结构👉专栏:数据结构啦

目录
❀前言
📕得到某年某月的天数
🧠普通闰年
🧠世纪闰年
📕得到某年某月的天数
📕判断日期的合法性
📕训练:第n天的日期
🧠第n天的日期参考代码
📕训练:日期距离
🧠日期距离参考代码
前言
无论是中小学编程竞赛还是大学生编程竞赛,日期模拟都是经常会出现的题目。
日期模拟经常会出现以下题型:
- 得到某年某月的天数
 - 判断给定日期的合法性
 - 给定年份,求这一年第n天的日期
 - 给定年月日,求经过n天后的日期
 - 查找两个日期之间有多少个回文日期... ...
 
得到某年某月的天数
得到某年某月的天数问题经常会作为其他问题的模板来使用。
首先我们需要存储一年中所有月份相对应的天数
int day[] = {0,31,28,31,30,31,30,31,31,30,31,30,31} 
其中day[1]表示一月份最多31天,2月份先赋值为28天,具体天数还需要检测年份是否是闰年,如果是闰年还需要+1天
闰年分为两种:
普通闰年
年份是4的倍数,但不是100的倍数,例如2004、2020年等
世纪闰年
是400的倍数,例如1900不是世纪闰年,2000是世纪闰年,即:
if(year % 4 == 0 && year % 100 != 0 || year % 400 == 0)
    是闰年;
else
    不是; 
 
得到某年某月的天数
当月份不是2月时,就返回指定当前月份初始天数
当月份是2月时,判断年份是否是闰年,当年份为闰年成立时,leap值为1,不成立时值为0,初始天数加上leap的值即为2月份天数
int days[] = {0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
// 得到某年某月的天数
int check(int y, int m)
{
    if(m != 2) return days[m];
    else
    {
        //特判 2 月
        int leap = (y % 4 == 0 && y % 100 != 0 || y % 400 == 0);
        return days[m] + leap;
    }
} 
 
判断日期的合法性
一般这样的题型会先给你一个格式,看是否符合这个格式,比如要满足20230701这样的格式才是合法的。
首先你需要分离出年份,再分离出月份,最后分离出日。
再分别判断年月日是否符合题意
if(m<1||m>12) 则月份不符合
if(d<1||d>(指定月份的总天数)) 则日不符合 
注:年份一般不需要检查,但也要视题意而定
训练:第n天的日期
给定一个年份y和一个整数d,问这一年的第d天是几月几日?注意闰年的2月有29天。满足下面条件之一的是闰年:
1、年份是4的整数倍,而且不是100的整数倍;
2、年份是400的整数倍。
【输入描述】输入的第一行包含一个整数y,表示年份,年份在1900到2015之间(包含1900和2015)。
输入的第二行包含一个整数d,d在1至365之间。
【输出描述】输出两行,每行一个整数,分别表示答案的月份和日期。
【样例输入1】
2015
80
【样例输出】
3
21
第n天的日期参考代码
#include <iostream>
using namespace std;
int day[13]={0,31,0,31,30,31,30,31,31,30,31,30,31};
bool check(int n)  //判断闰年
{
    if(n%400==0||(n%4==0&&n%100!=0)) return true;
    return false;
}
int main()
{
    int m,n;
    cin>>m>>n;
    if(check(m))  day[2]=29;
    else  day[2]=28;
    for(int j=1;j<=12;j++)
    {
        n-=day[j];
        if(n<0){
            cout<<j<<endl<<day[j]+n;
            break;
        }
        if(n==0)
        {
            cout<<j<<endl<<day[j];
            break;
        }
    }
    return 0;
} 
 
训练:日期距离
输入一个的日期,输出它和2014年5月17日相差有多少天?注意闰年的2月有29天。满足下面条件之一的是闰年:
1、年份是4的整数倍,而且不是100的整数倍;
2、年份是400的整数倍。
【输入描述】输入的第一行包含一个整数y,表示年份,年份在1到2014之间(包含1和2014)。
输入的第二行包含一个整数m,表示月份,m在1至12之间。
输入的第三行包含一个正整数d,表示日期,d在1至31之间。
【输出描述】输出两个日期之间相差的天数。
【输入样例】
1988
7
3
【输出样例】
9449
日期距离参考代码
#include <iostream>
using namespace std;
int day[13]={0,31,0,31,30,31,30,31,31,30,31,30,31};
bool check(int k)  //判断闰年
{
    if(k%400==0||(k%4==0&&k%100!=0))
        return true;
    return false;
}
int sum;//计算总天数
int main()
{
    int m,n,d;
    cin>>m>>n>>d;
    if(check(m))  day[2]=29;
    else  day[2]=28;
    for(int i=m+1;i<2014;i++)  //计算完整的年份天数
    {
        if(check(i))  sum+=366;
        else sum+=365;
    }
    if(m==2014)
    {
        for(int i=n+1;i<5;i++) //计算完整的月份的天数
            sum+=day[i];
        if(n==5) sum+=17-d;
        else sum+=day[n]-d+17;
    }
    else
    {
        sum+=137; //2014.1.1~2014.5.17总天数
        for(int i=n+1;i<=12;i++)   //算上完整月份天数
        sum+=day[i];
        sum+=day[n]-d;   
    }
    cout<<sum<<endl;
    return 0;
} 
从入门到算法,再到数据结构,查看全部文章请点击此处
http://www.bigbigli.com/



















