目录
一,万年历的基本要求
前言:万年历的创建思路
日历,要求日期与星期对应。基本格式输出就是,要求在一月内,从该月起始日到该月终止日,每一日都与星期相对应,因此,可以根据日期对天数7取余来完成对应。
其次,在一年内,每月都有属于自己的日期数,比如11月有30天。每一月份对应日历相互独立,(我们不可能将11月30日与12月1日连在一起,因为实际生活中的日历就不是这样的)。然而,需要注意到的是,虽然在日历上,它们处于两个不同日历月份,但在日期上他们只差一天,在星期上,它们也是两个相连的星期。因此,我们可以确定两个基本思路:
1.每一月份要规定最大日期,避免溢出,也规范了输出。
2.要确定某一日为参照日,用目标日减去参照日,得到距离日期,就可以做到本月末与下月初日期相连。
自然,要创作公元后日历,我们选用公元一年一月一日作为参照日,为1 。 这样我们确定了基本思路。
规定公元1年1月1日为1后,查找它对应的星期可以得到,为星期六,我们的两个起始点都确定,下面可以根据思路具体实现。
1.公元天数与日期
在确定了参照日后,我们假设要计算某一年某一月某一日的日数,
比如1900年5月21日,那么,我们必须用1900年以前所有年包含的日数,
加上前4月的所有日期数,再加上21,就得到了距离天数,再拿距离天数
加上某一特定数字(该数字作用是得到正确星期,因为参照日为星期六 )
对7取余,就可以得到该日的正确星期。
1.日期输入问题
首先,我们创造了一个日期转换函数,作用是得到某年某日某月距离参照日的日期。因此,参数输入为 年,月,日;返回参数为日期。
int Date_to_day(int y, int m, int d)
那我们定义该函数的第一件事,就是规避错误输入 ,避免后续错误发生的可能。错误输入就包括:年份,月份,日期不能为负数,不能超过对应最大值。
因此,先设立两个枚举,其中包括除二月份外每一月份的天数最大值,以及二月份在平闰年的天数最大值。
//月份天数最大值
enum Month_d
{
Jan_d = 31, Mar_d = 31,
Apri_d = 30, May_d = 31,
Jun_d = 30, Jul_d = 31,
Aug_d = 31, Sep_d = 30,
Oct_d = 31, Nov_d = 30, Dec_d = 31
};
enum Month_leap_d { Feb_d = 28, Feb_ld = 29 };
//枚举创建数组
static int month_darray[11] =
{
Jan_d,Mar_d,Apri_d,May_d,
Jun_d,Jul_d,Aug_d,Sep_d,
Oct_d,Nov_d,Dec_d
};
在函数内设立输入判断条件:
//排除基本输入错误
if (y < 1 || m < 1 || m>12 || d < 1 || d>31)
{
cout << "输入错误.程序结束.\n";
exit(EXIT_FAILURE);
}
//排除平年输入错误
if (y % 4 != 0&&m==2)
if (d > Feb_d)
{
cout << "输入错误.程序结束.\n";
exit(EXIT_FAILURE);
}
//补丁(排除定日期月份超出限额问题)
if (m == 1)
{
if (d > month_darray[0])
{
cout << "输入日期不符实际,超出月份上限,程序结束。\n";
exit(EXIT_FAILURE);
}
}
else if (m > 2)
{
if (d > month_darray[m - 2])
{
cout << "输入日期不符实际,超出月份上限,程序结束。\n";
exit(EXIT_FAILURE);
}
}
由于不能被4整除的年份一定是平年,因此在开头,我们先在开头排除了平年对程序的影响。在讨论闰年平年定义时,我们再对不足进行进一步补全。
2.闰年与平年的数目
现在日历上对闰年的定义为四年一闰百年不闰,每四百年再一闰。因此我们可以根据输入年数,该年(包括该年)以前共有多少闰年,多少平年。
再根据数目将年数转化为天数:
//得到1~y年的闰年平年数目
int lead_y1 = y / 4;
int lead_y2 = y / 100;
int lead_y3 = y / 400;
int total_lead = 0;
total_lead = lead_y1 - lead_y2 + lead_y3+(JUDE_Y/100-JUDE_Y/400);
//得到平年年数数目;
int total_com = y - total_lead;
//之前的年数转化为日(包括今年)
int total_yday = total_lead * leap_year_day + total_com * year_day;
其中,上述代码块设定了常量值:
//声明使用常量
static const int leap_year_day = 366;
static const int year_day = 365;
在根据四年一闰百年不闰,每四百年再一闰的定义,对闰年判断,得到目标天数。
月份转化为天数:
//月份转化为日(不包括2月以及本月)
int total_mday = 0;
if (2 == m)
total_mday += month_darray[m - 1];
else
{
for (int i = 0; i < m - 2; i++)//不能加上本月份
total_mday += month_darray[i];
}
if ((0 == y % 4) && (0 != y % 100) || (0 == y % 400))//闰年
{
total_yday -= leap_year_day;
if (m > 2)
total_mday += Feb_ld;
fe = 1;
}
else
{
total_yday -= year_day;
if (m > 2)
total_mday += Feb_d;
fe = 0;
}
//补丁(排除二月份日期溢出的问题)
if (m == 2 && 0 == fe)
{
if (d > Feb_d)
{
cout << "输入日期不符实际,超出月份上限,程序结束。\n";
exit(EXIT_FAILURE);
}
}
else if (2 == m && 1 == fe)
{
if (d > Feb_ld)
{
cout << "输入日期不符实际,超出月份上限,程序结束。\n";
exit(EXIT_FAILURE);
}
}
//年月日对应的日数
int total_day = total_mday + total_yday + d;
总天数:
//年月日对应的日数
int total_day = total_mday + total_yday + d;
3.日历的输出问题
1.日数转化为星期
至此,我们得到了基本正确的目标天数,可以将它加上一个数字对7取余,便得到了对应的星期数:
//日期转星期换算
int day_to_weekday(int n)
{
//公元1年1月1日是星期六
static const int pud_day = 5;
int weekday =(pud_day+n)%7;
return weekday;
}
设立一个数组保存需要输出星期日期。
const char weekDay[16] = { "日一二三四五六" };
然后再制作一个函数,输出该日期对应的星期:
//星期输出问题
void weekday(int n)
{
std::cout << "该日期为:星期" << weekDay[n * 2] << weekDay[n * 2 + 1] << std::endl;
}
需要注意的是,汉字储存需要两个字节连续储存,因此输出时也因连续输出两个字节。
至此,日期得到对应星期的工作基本完成。
运行截图如下:
该图片为最终代码运行输出与实况并不相同
2.日历月份开头
日历的表头一般是”日一二三四五六“。
因此可以创建一个表头函数,在每次显示日历时在函数中调用该表头。
//日历表头
void Cal_week()
{
std::cout << "日\t一\t二\t三\t四\t五\t六\n";
};
同时,根据得到的函数取余返回值,可以利用循环得到日历表前空白:
Cal_week();//表头
for (int j = 0; j < week_day; j++)
cout << " \t";//表首
此时,输出的具体日历,需要根据该年的闰平年情况进行判断,因此设立变量作为判断返回结果:
if ((0 == n % 4) && (0 != n % 100) || (0 == n % 400))//闰年
fe = 1;
else
fe = 0;
然后根据每个月,月初距离参照日的目标天数对七取余的返回值,以及该月份最大值,便可输出得到日历:
部分参数设定:
//平年
static int month_D[12] =
{
Jan_d,Feb_d,Mar_d,Apri_d,May_d,
Jun_d,Jul_d,Aug_d,Sep_d,
Oct_d,Nov_d,Dec_d
};
//闰年
static int month_LD[12] =
{
Jan_d,Feb_ld,Mar_d,Apri_d,May_d,
Jun_d,Jul_d,Aug_d,Sep_d,
Oct_d,Nov_d,Dec_d
};
日历输出代码块:
for (int i = 0; i < 12; i++)
{
int week_day = Date_to_day(n, Month_array[i], 1);
//制作日历表
cout << '\t' << i + 1 << "月\n";
Cal_week();//表头
for (int j = 0; j < week_day; j++)
cout << " \t";//表首
if (fe == 1)
{
for (int n = 1; n <= month_LD[i]; n++)
{
cout << n << '\t';
if (0 == (n + week_day) % 7)
cout << endl;
}
}
else
{
for (int n = 1; n <= month_D[i]; n++)
{
cout << n << '\t';
if (0 == (n + week_day) % 7)
cout << endl;
}
}
cout << endl;
};
至此,输出万年历的基本操作完成。
以下为运行截图:
该图片为最终代码运行输出与实况并不相同
但如果我们细心观察,就会发现,日历与星期对不上,并且差距较大。这是为什么呢?
并不是程序运行出了什么差错,而是,闰年的定义经过了变更。
为保证万年历的正确性,下面我们要讨论闰年的定义补充。
二,万年历正确性的额外补丁
凡公历中有闰日(2月29日)的年份,阴阳历中有闰月的年份。
1582年以来公历的置闰规则:
普通闰年:公历年份是4的倍数,且不是100的倍数的,为闰年
(如2004年、2020年等就是闰年)。
世纪闰年:公历年份是整百数的,必须是400的倍数才是闰年
(如1900年不是闰年,2000年是闰年)。
1582年以前的惯例:四年一闰;
也就是说,如果我们按1582年以来的闰年定义来得到公元1年以后的日历的话,偏差会越来越大。
因此为了解决这个偏差,我们对日期转化函数进行了分段更进。
以1583前为一段,以1583开始为一段。
1.1582年闰年定义的变更解决
对闰年定义分段,则会得到两种闰年和平年的数目。
如果在转化函数内对日期分段,再将得到的日期转化为星期。在第一步的分段分析,再将数字相加将会很麻烦。
因此,我们不妨如同将公元1年1月1日作为参照日那样,将1583年1月1日作为参考日,即:
1.在1583年以前(输入年数小于1583),用四年一闰的方法,判断闰年数可以得到正确日期。
2.在1583年以后,输入的年份用现在定义的闰年方法定义(此时得到的日期数是错误的),减去用现在定义的闰年方法定义的1583年以前的错误日期(此时得到的1583年以前的日期也是错误的),就得到了1583年以后的日期相对于1583年1月1日的正确的距离天数。
即抛弃之前的错误,使用参照日为1583年1月1日的正确天数。
改进后代码块:
(1)平闰年数目以及年月转化:
//得到1~y年的闰年平年数目
int lead_y1 = y / 4;
int lead_y2 = y / 100;
int lead_y3 = y / 400;
int total_lead = 0;
if (y < 1583)
total_lead = lead_y1;
else
total_lead = lead_y1 - lead_y2 + lead_y3+(JUDE_Y/100-JUDE_Y/400);
//得到平年年数数目;
int total_com = y - total_lead;
//之前的年数转化为日(包括今年)
int total_yday = total_lead * leap_year_day + total_com * year_day;
//月份转化为日(不包括2月以及本月)
int total_mday = 0;
if (2 == m)
total_mday += month_darray[m - 1];
else
{
for (int i = 0; i < m - 2; i++)//不能加上本月份
total_mday += month_darray[i];
}
(2)1583年以前日期转化为天数:
if (y < 1583)
{
if (0 == y % 4)//闰年
{
total_yday -= leap_year_day;
if (m > 2)
total_mday += Feb_ld;
fe = 1;
}
else
{
total_yday -= year_day;
if (m > 2)
total_mday += Feb_d;
fe = 0;
}
//补丁(排除二月份日期溢出的问题)
if (m == 2 && 0 == fe)
{
if (d > Feb_d)
{
cout << "输入日期不符实际,超出月份上限,程序结束。\n";
exit(EXIT_FAILURE);
}
}
else if (2 == m && 1 == fe)
{
if (d > Feb_ld)
{
cout << "输入日期不符实际,超出月份上限,程序结束。\n";
exit(EXIT_FAILURE);
}
}
//年月日对应的日数
int total_day = total_mday + total_yday + d;
(3)1583年后:
//定义的常量:
static const int JUDE_YEAR = 1582 / 4 * leap_year_day + (1582 - 1582 / 4) * year_day;
static const int JUDE_Y = 1582;
else
{
//闰年新制定的日历方法
total_yday -= JUDE_YEAR;
if ((0 == y % 4) && (0 != y % 100) || (0 == y % 400))//闰年
{
total_yday -= leap_year_day;
if (m > 2)
total_mday += Feb_ld;
fe = 1;
}
else
{
total_yday -= year_day;
if (m > 2)
total_mday += Feb_d;
fe = 0;
}
//补丁(排除二月份日期溢出的问题)
if (m == 2 && 0 == fe)
{
if (d > Feb_d)
{
cout << "输入日期不符实际,超出月份上限,程序结束。\n";
exit(EXIT_FAILURE);
}
}
else if (2 == m && 1 == fe)
{
if (d > Feb_ld)
{
cout << "输入日期不符实际,超出月份上限,程序结束。\n";
exit(EXIT_FAILURE);
}
}
//年月日对应的日数
int total_day = total_mday + total_yday + d;
再如同定义公元1年1月1日那样,定义它:
//1582年后
int day_to_weekday_new(int n)
{
//公元1583年1月1日是星期六
static const int Pud_day = 5;
int weekday = (Pud_day + n) % 7;
return weekday;
}
再调用该函数即可:
//年月日对应的日数
int total_day = total_mday + total_yday + d;
//调用函数
int wday = day_to_weekday_new(total_day);
cout << "公元" << y << "年" << m << "月" << d << "日\t";
weekday(wday);
这样,分段处理后,再搭配日历输出函数,便可以输出精准正确的星期与日历。
2.1582年消失的十天
下面,是1582年10月日历上消失的十天。
按照上述程序,程序以及可以完美实现公元后任意一年的日历输出。
但1582年有特殊情况:1582年10月5~14号并不存在,因此,要进行一下操作改进程序:
1.规避输入: 使程序判断输入该日期时,结果为false。
//判断是否在1582年后
int Jude_year = 1582;
//补丁:
//特殊情况: 1582年10月5~14输入为错误,消失的十天
if(y==Jude_year&&m==Oct)
if (4< d && d < 15)
{
cout << "1582年10月" << d << "日不存在于日历中。\n";
exit(EXIT_FAILURE);
}
2.输出日期对应星期: 1582年十月消失10天,因此,10月5日以前可以使用四年一闰的方法得到正确日期,而10月14日以后,得到日期的总数要减去10。
因此,加一个判断条件(加在y<1583的条件语句块里):
//年月日对应的日数
int total_day = total_mday + total_yday + d;
//平年判断补丁
//补丁(1582年特殊情况)
if (y == Jude_year && m == Oct)
{
if (d > 14)
{
total_day -= 10;
}
}
else if (y == Jude_year && m > Oct)
{
total_day -= 10;
}
//调用函数
int wday = day_to_weekday(total_day);
cout << "公元" << y << "年" << m << "月" << d << "日\t";
weekday(wday);
这样可以得到正确星期。
3.输出正确日历:
辅助函数:
//1582年11月1日为星期一
int day_to_weekday_1582(int n)
{
//公元1583年11月1日是星期一
static const int Pud_day = 5;
if (n == Nov)
{
int weekday = (Pud_day + 3) % 7;
return weekday;
}
//12月1日是星期三
else if (n == Dec)
{
int weekday = (Pud_day + 5) % 7;
return weekday;
}//10月1日为星期一
else if (n == Oct)
{
int weekday = (Pud_day + 3) % 7;
return weekday;
}
}
输出日历部分:
if (n == 1582)
{
fe = 0;
//1~9月份的日期
for (int i = 0; i < 9; i++)
{
int week_day = Date_to_day(n, Month_array[i], 1);
//制作日历表
cout << '\t' << i + 1 << "月\n";
Cal_week();//表头
for (int j = 0; j < week_day; j++)
cout << " \t";//表首
for (int n = 1; n <= month_D[i]; n++)
{
cout << n << '\t';
if (0 == (n + week_day) % 7)
cout << endl;
}
cout << endl;
};
//10月
{
int week_day = day_to_weekday_1582(Oct);
cout << "公元" << JUDE_Y << "年" << Oct<< "月" << 1 << "日\t";
weekday(week_day);
cout << '\t' << Oct << "月\n";
Cal_week();//表头
for (int j = 0; j < week_day; j++)
cout << " \t";//表首
for (int n = 1; n <= 4; n++)
{
cout << n << '\t';
if (0 == (n + week_day) % 7)
cout << endl;
}
for (int n = 15; n <= 31; n++)
{
cout << n << '\t';
if (0 == (n + week_day-10) % 7)
cout << endl;
}
cout << endl;
};
//11~12月
for (int i = 10; i < 12; i++)
{
int week_day = day_to_weekday_1582(i + 1);
cout << "公元" << JUDE_Y << "年" << i+1 << "月" << 1 << "日\t";
weekday(week_day);
//制作日历表
cout << '\t' << i + 1 << "月\n";
Cal_week();//表头
for (int j = 0; j < week_day; j++)
cout << " \t";//表首
for (int n = 1; n <= month_D[i]; n++)
{
cout << n << '\t';
if (0 == (n + week_day) % 7)
cout << endl;
}
cout << endl;
};
return;//结束进程
}
运行结果截图:
至此,程序结束,万年历制作完成。
三,万年历程序的组成函数
代码部分仅供参考
1.程序使用常量的设定
//声明使用常量
static const int leap_year_day = 366;
static const int year_day = 365;
//补丁
static const int JUDE_YEAR = 1582 / 4 * leap_year_day + (1582 - 1582 / 4) * year_day;
static const int JUDE_Y = 1582;
enum Month{ZERO,Jan, Feb, Mar, Apri, May, Jun, Jul, Aug, Sep, Oct, Nov,Dec };
//月份天数最大值
enum Month_d
{
Jan_d = 31, Mar_d = 31,
Apri_d = 30, May_d = 31,
Jun_d = 30, Jul_d = 31,
Aug_d = 31, Sep_d = 30,
Oct_d = 31, Nov_d = 30, Dec_d = 31
};
enum Month_leap_d { Feb_d = 28, Feb_ld = 29 };
//声明使用数组
static int Month_array[12] =
{Jan, Feb, Mar, Apri, May, Jun, Jul, Aug, Sep, Oct, Nov,Dec};
static int month_darray[11] =
{
Jan_d,Mar_d,Apri_d,May_d,
Jun_d,Jul_d,Aug_d,Sep_d,
Oct_d,Nov_d,Dec_d
};
//平年
static int month_D[12] =
{
Jan_d,Feb_d,Mar_d,Apri_d,May_d,
Jun_d,Jul_d,Aug_d,Sep_d,
Oct_d,Nov_d,Dec_d
};
//闰年
static int month_LD[12] =
{
Jan_d,Feb_ld,Mar_d,Apri_d,May_d,
Jun_d,Jul_d,Aug_d,Sep_d,
Oct_d,Nov_d,Dec_d
};
const char weekDay[16] = { "日一二三四五六" };
2.辅助函数
表头函数:
//日历表头
void Cal_week()
{
std::cout << "日\t一\t二\t三\t四\t五\t六\n";
};
输出星期函数:
//星期输出问题
void weekday(int n)
{
std::cout << "该日期为:星期" << weekDay[n * 2] << weekDay[n * 2 + 1] << std::endl;
}
换算日历函数(3个):
//日期转星期换算
int day_to_weekday(int n)
{
//公元1年1月1日是星期六
static const int pud_day = 5;
int weekday =(pud_day+n)%7;
return weekday;
}
//1582年后
int day_to_weekday_new(int n)
{
//公元1583年1月1日是星期六
static const int Pud_day = 5;
int weekday = (Pud_day + n) % 7;
return weekday;
}
//1582年11月1日为星期一
int day_to_weekday_1582(int n)
{
//公元1583年11月1日是星期一
static const int Pud_day = 5;
if (n == Nov)
{
int weekday = (Pud_day + 3) % 7;
return weekday;
}
//12月1日是星期三
else if (n == Dec)
{
int weekday = (Pud_day + 5) % 7;
return weekday;
}//10月1日为星期一
else if (n == Oct)
{
int weekday = (Pud_day + 3) % 7;
return weekday;
}
}
3.天数转化星期(其中有函数调用)
//日期换算
int Date_to_day(int y, int m, int d)
{
using std::cout;
using std::endl;
using std::cin;
//排除基本输入错误
if (y < 1 || m < 1 || m>12 || d < 1 || d>31)
{
cout << "输入错误.程序结束.\n";
exit(EXIT_FAILURE);
}
//排除平年输入错误
if (y % 4 != 0&&m==2)
if (d > Feb_d)
{
cout << "输入错误.程序结束.\n";
exit(EXIT_FAILURE);
}
//补丁(排除定日期月份超出限额问题)
if (m == 1)
{
if (d > month_darray[0])
{
cout << "输入日期不符实际,超出月份上限,程序结束。\n";
exit(EXIT_FAILURE);
}
}
else if (m > 2)
{
if (d > month_darray[m - 2])
{
cout << "输入日期不符实际,超出月份上限,程序结束。\n";
exit(EXIT_FAILURE);
}
}
//得到1~y年的闰年平年数目
int lead_y1 = y / 4;
int lead_y2 = y / 100;
int lead_y3 = y / 400;
int total_lead = 0;
if (y < 1583)
total_lead = lead_y1;
else
total_lead = lead_y1 - lead_y2 + lead_y3+(JUDE_Y/100-JUDE_Y/400);
//得到平年年数数目;
int total_com = y - total_lead;
//之前的年数转化为日(包括今年)
int total_yday = total_lead * leap_year_day + total_com * year_day;
//月份转化为日(不包括2月以及本月)
int total_mday = 0;
if (2 == m)
total_mday += month_darray[m - 1];
else
{
for (int i = 0; i < m - 2; i++)//不能加上本月份
total_mday += month_darray[i];
}
//判断本年是否为闰年
int fe = 0;
//判断是否在1582年后
int Jude_year = 1582;
//补丁:
//特殊情况: 1582年10月5~14输入为错误,消失的十天
if(y==Jude_year&&m==Oct)
if (4< d && d < 15)
{
cout << "1582年10月" << d << "日不存在于日历中。\n";
exit(EXIT_FAILURE);
}
//得到年月的总日数
//1583年以前的闰年规则
if (y < 1583)
{
if (0 == y % 4)//闰年
{
total_yday -= leap_year_day;
if (m > 2)
total_mday += Feb_ld;
fe = 1;
}
else
{
total_yday -= year_day;
if (m > 2)
total_mday += Feb_d;
fe = 0;
}
//补丁(排除二月份日期溢出的问题)
if (m == 2 && 0 == fe)
{
if (d > Feb_d)
{
cout << "输入日期不符实际,超出月份上限,程序结束。\n";
exit(EXIT_FAILURE);
}
}
else if (2 == m && 1 == fe)
{
if (d > Feb_ld)
{
cout << "输入日期不符实际,超出月份上限,程序结束。\n";
exit(EXIT_FAILURE);
}
}
//年月日对应的日数
int total_day = total_mday + total_yday + d;
//平年判断补丁
//补丁(1582年特殊情况)
if (y == Jude_year && m == Oct)
{
if (d > 14)
{
total_day -= 10;
}
}
else if (y == Jude_year && m > Oct)
{
total_day -= 10;
}
//调用函数
int wday = day_to_weekday(total_day);
cout << "公元" << y << "年" << m << "月" << d << "日\t";
weekday(wday);
return wday;
}
//1583年后的闰年规则
else
{
//闰年新制定的日历方法
total_yday -= JUDE_YEAR;
if ((0 == y % 4) && (0 != y % 100) || (0 == y % 400))//闰年
{
total_yday -= leap_year_day;
if (m > 2)
total_mday += Feb_ld;
fe = 1;
}
else
{
total_yday -= year_day;
if (m > 2)
total_mday += Feb_d;
fe = 0;
}
//补丁(排除二月份日期溢出的问题)
if (m == 2 && 0 == fe)
{
if (d > Feb_d)
{
cout << "输入日期不符实际,超出月份上限,程序结束。\n";
exit(EXIT_FAILURE);
}
}
else if (2 == m && 1 == fe)
{
if (d > Feb_ld)
{
cout << "输入日期不符实际,超出月份上限,程序结束。\n";
exit(EXIT_FAILURE);
}
}
//年月日对应的日数
int total_day = total_mday + total_yday + d;
//调用函数
int wday = day_to_weekday_new(total_day);
cout << "公元" << y << "年" << m << "月" << d << "日\t";
weekday(wday);
return wday;
}
}
3.日历输出函数
//输出日历
void month_Calendar(int n)
{
using std::cout;
using std::endl;
cout << "年份:" << n << " 年\n";
//该年是否为闰年的判断依据
int fe;
//考虑特殊情况 1582年
if (n == 1582)
{
fe = 0;
//1~9月份的日期
for (int i = 0; i < 9; i++)
{
int week_day = Date_to_day(n, Month_array[i], 1);
//制作日历表
cout << '\t' << i + 1 << "月\n";
Cal_week();//表头
for (int j = 0; j < week_day; j++)
cout << " \t";//表首
for (int n = 1; n <= month_D[i]; n++)
{
cout << n << '\t';
if (0 == (n + week_day) % 7)
cout << endl;
}
cout << endl;
};
//10月
{
int week_day = day_to_weekday_1582(Oct);
cout << "公元" << JUDE_Y << "年" << Oct<< "月" << 1 << "日\t";
weekday(week_day);
cout << '\t' << Oct << "月\n";
Cal_week();//表头
for (int j = 0; j < week_day; j++)
cout << " \t";//表首
for (int n = 1; n <= 4; n++)
{
cout << n << '\t';
if (0 == (n + week_day) % 7)
cout << endl;
}
for (int n = 15; n <= 31; n++)
{
cout << n << '\t';
if (0 == (n + week_day-10) % 7)
cout << endl;
}
cout << endl;
};
//11~12月
for (int i = 10; i < 12; i++)
{
int week_day = day_to_weekday_1582(i + 1);
cout << "公元" << JUDE_Y << "年" << i+1 << "月" << 1 << "日\t";
weekday(week_day);
//制作日历表
cout << '\t' << i + 1 << "月\n";
Cal_week();//表头
for (int j = 0; j < week_day; j++)
cout << " \t";//表首
for (int n = 1; n <= month_D[i]; n++)
{
cout << n << '\t';
if (0 == (n + week_day) % 7)
cout << endl;
}
cout << endl;
};
return;//结束进程
}
if (n < 1583)
{
if (0 == n % 4)//闰年
fe = 1;
else
fe = 0;
}
else
{
if ((0 == n % 4) && (0 != n % 100) || (0 == n % 400))//闰年
fe = 1;
else
fe = 0;
}
//星期余数
for (int i = 0; i < 12; i++)
{
int week_day = Date_to_day(n, Month_array[i], 1);
//制作日历表
cout << '\t' << i + 1 << "月\n";
Cal_week();//表头
for (int j = 0; j < week_day; j++)
cout << " \t";//表首
if (fe == 1)
{
for (int n = 1; n <= month_LD[i]; n++)
{
cout << n << '\t';
if (0 == (n + week_day) % 7)
cout << endl;
}
}
else
{
for (int n = 1; n <= month_D[i]; n++)
{
cout << n << '\t';
if (0 == (n + week_day) % 7)
cout << endl;
}
}
cout << endl;
};
}
代码如上仅供参考
如有不足,敬请指正。