题目描述:
计算当前时间的1秒后时间,并输出。
如输入当前时间2006年12月20日19时17分59秒,计算后输出时间是2006年12月20日19时18分00秒。
程序要求:
程序应该可以运行。通过控制台输入数据,输出数据通过printf给出;
1、实现思路(3种)
(1)if-else
(2)库函数
(3)表驱动
2、库函数
struct tm {
int tm_sec; /* seconds after the minute - [0,59] */
int tm_min; /* minutes after the hour - [0,59] */
int tm_hour; /* hours since midnight - [0,23] */
int tm_mday; /* day of the month - [1,31] */
int tm_mon; /* months since January - [0,11] */
int tm_year; /* years since 1900 */
int tm_wday; /* days since Sunday - [0,6] */
int tm_yday; /* days since January 1 - [0,365] */
int tm_isdst; /* daylight savings(夏令时) time flag */
};
(1)把输入转化成内部时间存储:根据输入对结构体依次赋值
(2)加一:转换成 time_t: 用函数time_t __cdecl mktime(struct tm *)实现,加一。
struct tm * __cdecl gmtime(const time_t *);
(3)输出:asctime();
char * __cdecl asctime(const struct tm *);
char * __cdecl ctime(const time_t *);
/* get the time of next sec */
struct tm * nextSec( struct tm * ptm )
{
time_t t = mktime( ptm ); //
t += 1;
ptm = localtime( &t );
return ptm;
}
3、表驱动
(1)月份天数查表
Month[2][12] (Month[2][13] )
|
|
1
|
2
|
3
|
4
|
5
|
6
|
7
|
8
|
9
|
10
|
11
|
12
|
|
0
|
31
|
28
|
31
|
30
|
31
|
30
|
31
|
31
|
30
|
31
|
30
|
31
|
|
1
|
31
|
29
|
31
|
30
|
31
|
30
|
31
|
31
|
30
|
31
|
30
|
31
|
判断闰年
int isLeapYear( int iYear )
{
return !(iYear % 4 )&&(iYear %100 )|| !( iYear %400 );
}
void NextSec_0( struct tm * ptm )
{
int c1 = 0;
int c2 = 0;
int isLeap;
int mon;
//秒
c1 = (ptm->tm_sec +1) / 60;
ptm->tm_sec = (ptm->tm_sec +1)% 60;
//分
c2 = (ptm->tm_min +1)/ 60;
ptm->tm_min = (ptm->tm_min + c1)% 60;
c1 = c2;
//时
c2 = (ptm->tm_hour +1)/ 24;
ptm->tm_hour = (ptm->tm_hour + c1) % 24;
c1 = c2;
//日
ptm->tm_mday -= 1; // 调整从[1~31] 到[0~30]
isLeap = isLeapYear( ptm->tm_year + 1900 );
mon = ptm->tm_mon;
c2 = (ptm->tm_mday + c1) / Month[isLeap][mon];
ptm->tm_mday = (ptm->tm_mday + c1) % Month[isLeap][mon];
c1 = c2;
ptm->tm_mday += 1;
//月
c2 = (ptm->tm_mon + c1) / 12;
ptm->tm_mon = (ptm->tm_mon + c1) % 12;
//年
ptm->tm_year += c2;
}
(2) 进一步查表
创建表:
|
60
|
60
|
24
|
*
|
12
|
1
|
|
SEC
|
MIN
|
HOUR
|
DAY
|
MON
|
YEAR
|
说明:第一行为权值,第二行为数位。类似普通加法。
*:表示不确定
1:不用进位
void NextSec_1( struct tm * ptm )
{
int i, isLeap, mon;
int c1,
c2;
/*==========下面建了两个表:第一个类似于普通数的数位==============*/
/*
* 第一个类似于普通数的数位;
* 第二个类似每位的权值
*/
int *t[NUM] = {
&ptm->tm_sec,
&ptm->tm_min,
&ptm->tm_hour,
&ptm->tm_mday,
&ptm->tm_mon,
&ptm->tm_year
};
int w[NUM] = {
60,
60,
24,
1, /* DAY */
12,
1 /* YEAR */
};
/* ======表初始化========= */
w[YEAR] = ptm->tm_year + 1900; //年份从1900年开始
isLeap = isLeapYear(w[YEAR]); //判断闰年
mon = *t[MON]; //得到当前月份(0~11)
w[DAY] = Month[isLeap][mon]; //取得当前月份的天数
*t[DAY] -= 1; // 调整mday【1`31】[0~30]
/*============下面是整个计算过程==============*/
c1 = 1; //下面的进位
c2 = 0; //向上的进位
for( i = SEC; i < YEAR; i++ )
{
c2 = (*t[i] + c1 ) / w[i]; // 记录进位
*t[i] = (*t[i] + c1 ) % w[i]; // 计算当前位
c1 = c2;
}
*t[YEAR] += c1; // 将进位加到最高位
*t[DAY] += 1; /* 调整mday【1`31】[0~30] */
}
发表于 @ 2007年11月09日 19:50:00|评论(loading...)|编辑