【综合】输出公历年历并标注指定日期
背景:
中国人很早就根据自己的天文知识、气候知识和农事规律发明并制定了历法,这又称年历年历主要有阳历(公历)、阴历和阴阳历三种。阳历以地球公转周期为依据:阴历以月相变化为依据:阴阳历结合两者特点。目前世界上最通用的是阳历,我国使用的一般是阴阳历。日常生活中,我们从年历中可以很方便地查询多种功能信息
输入:
从键盘输入 年-月-日 三项数据
输出:
1.按照相应格式输出该年份的年历(公历)
2.在该年历中标出所输日期,即在日期前后加星号 (‘ * ’)
合法年份为1000年至3000年,如果输入的日期不合法,则输出[精工BIT]图案
样例:
样例 1 :
- 输入
1-1-1↵
- 输出
+-----------------------------------------------------------------------------------------+ | | | ** | | *** ** | | *** ** ********* ********** *********** | | *** **** *** *** *** ** *** ** | | ** ** **** ***** *** *** *** ** *** * | | ** *** **** ******** *** *** *** ** *** * | | ** ** ** ***** ******* *** *** *** *** | | ******* ** *** *** *** *** *** *** | | ** ******** ** *** *** *** *** | | **** ***** ** ******** *** *** | | ******** *** ** *** *** *** *** | | ** *** ******** ** *** ** *** *** | | ****** ** ** ** *** *** *** *** | | ****** ******* ** *** *** *** *** | | ** ** ** ** ** *** *** *** *** | | *** ** ** ** *********** *** *** *** *** | | ** ** ***** ** ************ ** *** *** *** *** | | ** ** ** *** **** ********** ********* ***** | | ** ** *** | | ** ** ***** | | ** *** http://online.bit.edu.cn/ | | ** | | | +-----------------------------------------------------------------------------------------+
样例2:
- 输入:
2020-01-01↵
- 输出:
+-----------------------------------------------------------------------------------------+ | | | Calendar of Year [ 2 0 2 0 ] | | | +-----------------------------+-----------------------------+-----------------------------+ | Jan | Feb | Mar | +-----------------------------+-----------------------------+-----------------------------+ | Mon Tue Wed Thu Fri Sat Sun | Mon Tue Wed Thu Fri Sat Sun | Mon Tue Wed Thu Fri Sat Sun | | *1* 2 3 4 5 | 1 2 | 1 | | 6 7 8 9 10 11 12 | 3 4 5 6 7 8 9 | 2 3 4 5 6 7 8 | | 13 14 15 16 17 18 19 | 10 11 12 13 14 15 16 | 9 10 11 12 13 14 15 | | 20 21 22 23 24 25 26 | 17 18 19 20 21 22 23 | 16 17 18 19 20 21 22 | | 27 28 29 30 31 | 24 25 26 27 28 29 | 23 24 25 26 27 28 29 | | | | 30 31 | +-----------------------------+-----------------------------+-----------------------------+ | Apr | May | Jun | +-----------------------------+-----------------------------+-----------------------------+ | Mon Tue Wed Thu Fri Sat Sun | Mon Tue Wed Thu Fri Sat Sun | Mon Tue Wed Thu Fri Sat Sun | | 1 2 3 4 5 | 1 2 3 | 1 2 3 4 5 6 7 | | 6 7 8 9 10 11 12 | 4 5 6 7 8 9 10 | 8 9 10 11 12 13 14 | | 13 14 15 16 17 18 19 | 11 12 13 14 15 16 17 | 15 16 17 18 19 20 21 | | 20 21 22 23 24 25 26 | 18 19 20 21 22 23 24 | 22 23 24 25 26 27 28 | | 27 28 29 30 | 25 26 27 28 29 30 31 | 29 30 | | | | | +-----------------------------+-----------------------------+-----------------------------+ | Jul | Aug | Sep | +-----------------------------+-----------------------------+-----------------------------+ | Mon Tue Wed Thu Fri Sat Sun | Mon Tue Wed Thu Fri Sat Sun | Mon Tue Wed Thu Fri Sat Sun | | 1 2 3 4 5 | 1 2 | 1 2 3 4 5 6 | | 6 7 8 9 10 11 12 | 3 4 5 6 7 8 9 | 7 8 9 10 11 12 13 | | 13 14 15 16 17 18 19 | 10 11 12 13 14 15 16 | 14 15 16 17 18 19 20 | | 20 21 22 23 24 25 26 | 17 18 19 20 21 22 23 | 21 22 23 24 25 26 27 | | 27 28 29 30 31 | 24 25 26 27 28 29 30 | 28 29 30 | | | 31 | | +-----------------------------+-----------------------------+-----------------------------+ | Oct | Nov | Dec | +-----------------------------+-----------------------------+-----------------------------+ | Mon Tue Wed Thu Fri Sat Sun | Mon Tue Wed Thu Fri Sat Sun | Mon Tue Wed Thu Fri Sat Sun | | 1 2 3 4 | 1 | 1 2 3 4 5 6 | | 5 6 7 8 9 10 11 | 2 3 4 5 6 7 8 | 7 8 9 10 11 12 13 | | 12 13 14 15 16 17 18 | 9 10 11 12 13 14 15 | 14 15 16 17 18 19 20 | | 19 20 21 22 23 24 25 | 16 17 18 19 20 21 22 | 21 22 23 24 25 26 27 | | 26 27 28 29 30 31 | 23 24 25 26 27 28 29 | 28 29 30 31 | | | 30 | | +-----------------------------+-----------------------------+-----------------------------+ | | | ** 2020-01-01 | | *** ** | | *** ** ********* ********** *********** | | *** **** *** *** *** ** *** ** | | ** ** **** ***** *** *** *** ** *** * | | ** *** **** ******** *** *** *** ** *** * | | ** ** ** ***** ******* *** *** *** *** | | ******* ** *** *** *** *** *** *** | | ** ******** ** *** *** *** *** | | **** ***** ** ******** *** *** | | ******** *** ** *** *** *** *** | | ** *** ******** ** *** ** *** *** | | ****** ** ** ** *** *** *** *** | | ****** ******* ** *** *** *** *** | | ** ** ** ** ** *** *** *** *** | | *** ** ** ** *********** *** *** *** *** | | ** ** ***** ** ************ ** *** *** *** *** | | ** ** ** *** **** ********** ********* ***** | | ** ** *** | | ** ** ***** | | ** *** http://online.bit.edu.cn/ | | ** | | | +-----------------------------------------------------------------------------------------+
思路 main()
这种复杂的问题,我一般习惯简化为一个个函数
所以先研究主函数的思路:
- 首先从键盘获取年-月-日 这个简单
- 然后初始化(2月天数,以及其他需要初始化的变量)
- 判断是否合法
- 如果不合法:
- 打印BIT图样
- 如果合法:
- 然后打印年历头
- 然后重复四次
- 打印月份
- 打印星期
- 打印月历
- 打印结束BIT图样
main() 代码
int main()
{
int y, i;
scanf("%d-%d-%d", &y, &vm, &vd);
initialize(y);
sprintf(yy, "%d", y);
if (!OK(y, vm, vd)) return 0;
head(yy);
for (i = 1; i < 5; i++) body(i);
BIT(yy, vm, vd);
return 0;
}
初始化
其实就是判断是否为闰年,并把年份整型转化为字符串
void initialize(int y)
{
if (y % 4 == 0 && y % 100 != 0 || y % 400 == 0) a[2] = 29;
int ans = 1;
for (int i = 1; i < 13; i++)
{
if ((y - 1 + (y - 1) / 4 - (y - 1) / 100 + (y - 1) / 400 + ans) % 7 == 0)
Fday[i] = 7;
else
Fday[i] = (y - 1 + (y - 1) / 4 - (y - 1) / 100 + (y - 1) / 400 + ans) % 7;
ans += a[i];
}
sprintf(yy, "%d", y);
}
年历头
就是普通的打印
void head(char* y)
{
printf("+-----------------------------------------------------------------------------------------+\n");
printf("| |\n\
| Calendar of Year [ %c %c %c %c ] |\n\
| |\n", y[0], y[1], y[2], y[3]);
line();
}
主体部分(也就真正的年历部分)
void body(int group)
{
title(group);
line();
subtitle();
int m = 3 * group - 2;
int day1 = 1, day2 = 1, day3 = 1;
int* d1 = &day1, * d2 = &day2, * d3 = &day3;
for (int i = 0; i < 6; i++)
{
printf("| ");
month(m, d1);
printf(" ");
month(m + 1, d2);
printf(" ");
month(m + 2, d3);
printf("\n");
}
line();
}
打印横线
这个重复出现,所以我单独写了个函数
void line()
{
printf("+-----------------------------+-----------------------------+-----------------------------+\n");
}
打印月份和星期
void subtitle()
{
printf("| Mon Tue Wed Thu Fri Sat Sun | Mon Tue Wed Thu Fri Sat Sun | Mon Tue Wed Thu Fri Sat Sun |\n");
}
void title(int group)
{
switch (group)
{
case 1:
printf("| Jan | Feb | Mar |\n");
break;
case 2:
printf("| Apr | May | Jun |\n");
break;
case 3:
printf("| Jul | Aug | Sep |\n");
break;
case 4:
printf("| Oct | Nov | Dec |\n");
}
}
void month(int m, int* d)
{
if (*d == 1)
for (int i = 0; i < 7; i++)
{
if (Fday[m] != 1)
{
printf(" ");
Fday[m] --;
}
else
{
if (m == vm && *d == vd)
{
if (vd < 10)
printf(" *%d*", (*d)++);
else
printf("*%d*", (*d)++);
}
else
printf("%3d ", (*d)++);
}
}
else
for (int i = 0; i < 7; i++)
{
if (m == vm && *d == vd)
{
if (vd < 10)
printf(" *%d*", (*d)++);
else
printf("*%d*", (*d)++);
}
else if (*d <= a[m])
printf("%3d ", (*d)++);
else
printf(" ");
}
printf("|");
}
BIT图样/非法BIT图样
其实写一个就够了,但是我懒
void BIT(int y, int m, int d)
{
printf("| |\n\
| ** %4d-%02d-%02d |\n\
| *** ** |\n\
| *** ** ********* ********** *********** |\n\
| *** **** *** *** *** ** *** ** |\n\
| ** ** **** ***** *** *** *** ** *** * |\n\
| ** *** **** ******** *** *** *** ** *** * |\n\
| ** ** ** ***** ******* *** *** *** *** |\n\
| ******* ** *** *** *** *** *** *** |\n\
| ** ******** ** *** *** *** *** |\n\
| **** ***** ** ******** *** *** |\n\
| ******** *** ** *** *** *** *** |\n\
| ** *** ******** ** *** ** *** *** |\n\
| ****** ** ** ** *** *** *** *** |\n\
| ****** ******* ** *** *** *** *** |\n\
| ** ** ** ** ** *** *** *** *** |\n\
| *** ** ** ** *********** *** *** *** *** |\n\
| ** ** ***** ** ************ ** *** *** *** *** |\n\
| ** ** ** *** **** ********** ********* ***** |\n\
| ** ** *** |\n\
| ** ** ***** |\n\
| ** *** http://online.bit.edu.cn/ |\n\
| ** |\n\
| |\n\
+-----------------------------------------------------------------------------------------+\n", y, m, d);
}
int OK(int y, int m, int d)
{
if (y <= 3000 && y >= 1000 && m <= 12 && m >= 1 && d >= 1 && d <= a[m]) return 1;
printf("+-----------------------------------------------------------------------------------------+\n\
| |\n\
| ** |\n\
| *** ** |\n\
| *** ** ********* ********** *********** |\n\
| *** **** *** *** *** ** *** ** |\n\
| ** ** **** ***** *** *** *** ** *** * |\n\
| ** *** **** ******** *** *** *** ** *** * |\n\
| ** ** ** ***** ******* *** *** *** *** |\n\
| ******* ** *** *** *** *** *** *** |\n\
| ** ******** ** *** *** *** *** |\n\
| **** ***** ** ******** *** *** |\n\
| ******** *** ** *** *** *** *** |\n\
| ** *** ******** ** *** ** *** *** |\n\
| ****** ** ** ** *** *** *** *** |\n\
| ****** ******* ** *** *** *** *** |\n\
| ** ** ** ** ** *** *** *** *** |\n\
| *** ** ** ** *********** *** *** *** *** |\n\
| ** ** ***** ** ************ ** *** *** *** *** |\n\
| ** ** ** *** **** ********** ********* ***** |\n\
| ** ** *** |\n\
| ** ** ***** |\n\
| ** *** http://online.bit.edu.cn/ |\n\
| ** |\n\
| |\n\
+-----------------------------------------------------------------------------------------+\n");
return 0;
}
整体
这次我懒得优化了
这次同学们可以自己尝试简化这些代码
#include <stdio.h>
int a[13] = { 0,31,28,31,30,31,30,31,31,30,31,30,31 }, Fday[13] = { 0 }, vm, vd;
char yy[5];
void initialize(int y)
{
if (y % 4 == 0 && y % 100 != 0 || y % 400 == 0) a[2] = 29;
int ans = 1;
for (int i = 1; i < 13; i++)
{
if ((y - 1 + (y - 1) / 4 - (y - 1) / 100 + (y - 1) / 400 + ans) % 7 == 0)
Fday[i] = 7;
else
Fday[i] = (y - 1 + (y - 1) / 4 - (y - 1) / 100 + (y - 1) / 400 + ans) % 7;
ans += a[i];
}
sprintf(yy, "%d", y);
}
void line()
{
printf("+-----------------------------+-----------------------------+-----------------------------+\n");
}
void subtitle()
{
printf("| Mon Tue Wed Thu Fri Sat Sun | Mon Tue Wed Thu Fri Sat Sun | Mon Tue Wed Thu Fri Sat Sun |\n");
}
void head(char* y)
{
printf("+-----------------------------------------------------------------------------------------+\n");
printf("| |\n\
| Calendar of Year [ %c %c %c %c ] |\n\
| |\n", y[0], y[1], y[2], y[3]);
line();
}
void title(int group)
{
switch (group)
{
case 1:
printf("| Jan | Feb | Mar |\n");
break;
case 2:
printf("| Apr | May | Jun |\n");
break;
case 3:
printf("| Jul | Aug | Sep |\n");
break;
case 4:
printf("| Oct | Nov | Dec |\n");
}
}
void month(int m, int* d)
{
if (*d == 1)
for (int i = 0; i < 7; i++)
{
if (Fday[m] != 1)
{
printf(" ");
Fday[m] --;
}
else
{
if (m == vm && *d == vd)
{
if (vd < 10)
printf(" *%d*", (*d)++);
else
printf("*%d*", (*d)++);
}
else
printf("%3d ", (*d)++);
}
}
else
for (int i = 0; i < 7; i++)
{
if (m == vm && *d == vd)
{
if (vd < 10)
printf(" *%d*", (*d)++);
else
printf("*%d*", (*d)++);
}
else if (*d <= a[m])
printf("%3d ", (*d)++);
else
printf(" ");
}
printf("|");
}
void body(int group)
{
title(group);
line();
subtitle();
int m = 3 * group - 2;
int day1 = 1, day2 = 1, day3 = 1;
int* d1 = &day1, * d2 = &day2, * d3 = &day3;
for (int i = 0; i < 6; i++)
{
printf("| ");
month(m, d1);
printf(" ");
month(m + 1, d2);
printf(" ");
month(m + 2, d3);
printf("\n");
}
line();
}
void BIT(int y, int m, int d)
{
printf("| |\n\
| ** %4d-%02d-%02d |\n\
| *** ** |\n\
| *** ** ********* ********** *********** |\n\
| *** **** *** *** *** ** *** ** |\n\
| ** ** **** ***** *** *** *** ** *** * |\n\
| ** *** **** ******** *** *** *** ** *** * |\n\
| ** ** ** ***** ******* *** *** *** *** |\n\
| ******* ** *** *** *** *** *** *** |\n\
| ** ******** ** *** *** *** *** |\n\
| **** ***** ** ******** *** *** |\n\
| ******** *** ** *** *** *** *** |\n\
| ** *** ******** ** *** ** *** *** |\n\
| ****** ** ** ** *** *** *** *** |\n\
| ****** ******* ** *** *** *** *** |\n\
| ** ** ** ** ** *** *** *** *** |\n\
| *** ** ** ** *********** *** *** *** *** |\n\
| ** ** ***** ** ************ ** *** *** *** *** |\n\
| ** ** ** *** **** ********** ********* ***** |\n\
| ** ** *** |\n\
| ** ** ***** |\n\
| ** *** http://online.bit.edu.cn/ |\n\
| ** |\n\
| |\n\
+-----------------------------------------------------------------------------------------+\n", y, m, d);
}
int OK(int y, int m, int d)
{
if (y <= 3000 && y >= 1000 && m <= 12 && m >= 1 && d >= 1 && d <= a[m]) return 1;
printf("+-----------------------------------------------------------------------------------------+\n\
| |\n\
| ** |\n\
| *** ** |\n\
| *** ** ********* ********** *********** |\n\
| *** **** *** *** *** ** *** ** |\n\
| ** ** **** ***** *** *** *** ** *** * |\n\
| ** *** **** ******** *** *** *** ** *** * |\n\
| ** ** ** ***** ******* *** *** *** *** |\n\
| ******* ** *** *** *** *** *** *** |\n\
| ** ******** ** *** *** *** *** |\n\
| **** ***** ** ******** *** *** |\n\
| ******** *** ** *** *** *** *** |\n\
| ** *** ******** ** *** ** *** *** |\n\
| ****** ** ** ** *** *** *** *** |\n\
| ****** ******* ** *** *** *** *** |\n\
| ** ** ** ** ** *** *** *** *** |\n\
| *** ** ** ** *********** *** *** *** *** |\n\
| ** ** ***** ** ************ ** *** *** *** *** |\n\
| ** ** ** *** **** ********** ********* ***** |\n\
| ** ** *** |\n\
| ** ** ***** |\n\
| ** *** http://online.bit.edu.cn/ |\n\
| ** |\n\
| |\n\
+-----------------------------------------------------------------------------------------+\n");
return 0;
}
int main()
{
int y, i;
scanf("%d-%d-%d", &y, &vm, &vd);
initialize(y);
if (!OK(y, vm, vd)) return 0;
head(yy);
for (i = 1; i < 5; i++) body(i);
BIT(y, vm, vd);
return 0;
}