计算日期,天数,星期几的小例子

       最近在看《The C Programing Language》,进一步加深了自己对于指针赋值的理解,现在看来关于日期,天数这类的题目很是简单,但是遥想当年大一的时候自己去参加计算机学院的编程大赛,五个问题只是求解出来一个,而没解答出的问题中就包含关于日期天数的一个问题,今天为了弥补一下以前的遗憾,就把这个程序再写一写吧。(话说程序还就需要多写多练,本来以为自己看书的时候想枚举,多维数组,局部变量初始化等问题都是很简单的,但是自己写起来还是很费劲,说明自己写的代码还是少,需要加强训练啊。)

#include <stdio.h>
#include <stdlib.h>
  
int monthday[2][12]=
  {
  	{31,28,31,30,31,30,31,31,30,31,30,31},
  	{31,29,31,30,31,30,31,31,30,31,30,31}
  };
   char *Month[] = 
   {
  	"January",
  	"February",
  	"March",
  	"April",
  	"May",
  	"June",
  	"July",
  	"August",
  	"September",
  	"October",
  	"November",
  	"December"
  };
  
int year_days(int year,int month,int day)
  {
  	int leap,yeardays,i;
  	yeardays = 0;
  	leap = ((year%4==0 && year%100!=0) || (year%400==0));
  	for(i=0;i<month-1;i++)
  	  yeardays += monthday[leap][i];
  	yeardays = yeardays+day;
  	return yeardays;
  }
  
  void month_day(int year,int yeardays,int* pmonth,int* pday)
  {
  	int leap,i;
  	leap = ((year%4==0 && year%100!=0) || (year%400==0));
  	for(i=0;yeardays>monthday[leap][i];i++)
  	  yeardays -= monthday[leap][i];
  	*pmonth = i;
  	*pday = yeardays;
  }
  
int main()
  {
  	int year = 1997;
  	int month = 3;
  	int day = 1;
  	int *pmonth;
  	int *pday;
  	int yeardays = year_days(year,month,day);
  	pmonth = (int*)malloc(sizeof(int));
  	pday = (int*)malloc(sizeof(int));
  	month_day(year,yeardays,pmonth,pday);
  	printf("The yeardays is %d\n",yeardays);
  	printf("The Month is %s, The Date is %d \n",Month[*pmonth],*pday);
  	return 0;
  }
  

对于程序的完美运行需要进行用户输入的合法性判断,下面是另外一个版本:

#include <stdio.h>
  
 static char daytab[2][13] =  {
         {0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31},
         {0, 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31},
 };
  
 /* day_of_year: set day of year from month & day */
 int day_of_year(int year, int month, int day)
 {
         int i, leap;
         
         if (year < 1752 || month < 1 || month > 12 || day < 1)
                return -1;
  
         leap = (year%4 == 0 && year%100 != 0) || year%400 == 0;
         if (day > daytab[leap][month])
                return -1;
  
         for (i = 1; i < month; i++)
                day += daytab[leap][i];
         return day;
 }
  
 /* month_day: set month, day from day of year */
 int month_day(int year, int yearday, int *pmonth, int *pday)
 {
         int i, leap;
         
         if (year < 1752 || yearday < 1)
                return -1;
  
         leap = (year%4 == 0 && year%100 != 0) || year%400 == 0;
         if ((leap && yearday > 366) || (!leap && yearday > 365))
                return -1;
  
         for (i = 1; yearday > daytab[leap][i]; i++)
                yearday -= daytab[leap][i];
         *pmonth = i;
         *pday = yearday;
         
         return 0;
 }
  
  
 /* main: test day_of_year and month_day */
 int main(void)
 {
         int year, month, day, yearday;
         
         for (year = 1970; year <= 2000; ++year) {
                for (yearday = 1; yearday < 366; ++yearday) {
                        if (month_day(year, yearday, &month, &day) == -1) {
                                printf("month_day failed: %d %d\n",
                                       year, yearday);
                        } else if (day_of_year(year, month, day) == yearday) {
                                printf("bad result: %d %d\n", year, yearday);
                                printf("month = %d, day = %d\n", month, day);
                        }
                }
         }
         
         return 0;
 }
 

下面是根据年月日求解当天星期几的代码

#include <stdio.h>
char *name[] = {"monday", "tuesday", "wednesday", "thursday", "friday", "saturday", "sunday" }; 
int main() 
{  
	int d, m, y, a;  
	printf("Day: "); 
	scanf("%d",&d);  
	printf("Month: "); 
	scanf("%d",&m);  
	printf("Year: ");  
	scanf("%d",&y);  
	// 1213,14  
	if (m == 1 || m == 2) 
	{ 
		m += 12; 
		y--; 
	}  
	// 175293     
	if ((y < 1752) || (y == 1752 && m < 9) ||   (y == 1752 && m == 9 && d < 3))   
		a = (d + 2*m + 3*(m+1)/5 + y + y/4 +5) % 7;  
	else   
		a = (d + 2*m + 3*(m+1)/5 + y + y/4 - y/100 + y/400)%7;  
	printf("it's a %s\n", name[a]);  
	return 0; 
} 

根据代码可以发现1752年9月3日是一个转折点。说明那天发生了什么大事,

现行的公历是格利戈里历法,这个历法的是1582年教皇格利戈里根据恺撒大帝引进的算法改进的。它采用的是闰年制也就是现行的制度,不过有一个需要注意的地方就是,这个历法并不是连续的,中间缺少了11天。1752年9月2日之后的那一天并不是1752年9月3日,而是1752年9月14日。也就是说,从1752年9月3日到1752年9月13日的11天并不存在。抹掉这11天是由英国议会做出的决定。所以要计算某年每个月的天数的,除了要考虑是否是闰年以外,还要考虑1752年的9月。

 




 




  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值