1. 相关数据结构
- time_t
首先看time.h文件中队time_t的定义
#ifndef _TIME_T_DEFINED typedef long time_t; /* 时间值 */ #define _TIME_T_DEFINED /* 避免重复定义 time_t */ #endif
可以看出time_t实际上是一个整数,它记录了保存的是从1970年1月1日0时0分0 秒到现在经过的秒数。这里有一点要注意,对time_t数据类型的值来说,它所表示的时间不能晚于2038年1月18日19时14分07秒,否则会发生溢出。为了能够表示更久远的时间,一些编译器厂商引入了64位甚至更长的整形数来保存日历时间。
- struct tm
首先看time.h文件中队time_t的定义
#ifndef _TM_DEFINED struct tm { int tm_sec; /* 秒 – 取值区间为[0,59] */ int tm_min; /* 分 - 取值区间为[0,59] */ int tm_hour; /* 时 - 取值区间为[0,23] */ int tm_mday; /* 一个月中的日期 - 取值区间为[1,31] */ int tm_mon; /* 月份(从一月开始,0代表一月) - 取值区间为[0,11] */ int tm_year; /* 年份,其值等于实际年份减去1900 */ int tm_wday; /* 星期 – 取值区间为[0,6],其中0代表星期天,1代表星期一,以此类推 */ int tm_yday; /* 从每年的1月1日开始的天数 – 取值区间为[0,365],其中0代表1月1日,1代表1月2日,以此类推 */ int tm_isdst; /* 夏令时标识符,实行夏令时的时候,tm_isdst为正。不实行夏令时的进候,tm_isdst为0;不了解情况时,tm_isdst()为负。*/ }; #define _TM_DEFINED #endif
ANSI C标准称使用tm结构的这种时间表示为分解时间(broken-down time)。
- time_t和struct tm之间是可以相互转化的
在time.h文件中有如下两个函数
time_t mktime(struct tm * timeptr);
struct tm * localtime(const time_t * timer);
2. 时间加减
从上面对time_t和tm的分析你应该很容易想到如何进行时间的加减操作了吧。一种方法,我们可以对time_t类型的数据直接进行加减秒数操作。另一种方法,可以操作tm结构体内的变量。下面一个例子实现对当前时间加30分钟的操作。
#include <time.h> #include <stdio.h> int main( int argc, char *argv[] ) { time_t tmp_time; struct tm *ptime; struct tm *tmp; tmp_time = time(NULL);//获取当前时间 ptime = localtime(&tmp_time); printf("%d-%d-%d %d:%d:%d\n",(1900+ptime->tm_year),(1+ptime->tm_mon),ptime->tm_mday,\ ptime->tm_hour,ptime->tm_min,ptime->tm_sec); tmp_time += 30*60; tmp = localtime(&tmp_time); printf("%d-%d-%d %d:%d:%d\n",(1900+tmp->tm_year),(1+tmp->tm_mon),tmp->tm_mday,\ tmp->tm_hour,tmp->tm_min,tmp->tm_sec); ptime->tm_min += 30; printf("%d-%d-%d %d:%d:%d\n",(1900+ptime->tm_year),(1+ptime->tm_mon),ptime->tm_mday,\ ptime->tm_hour,ptime->tm_min,ptime->tm_sec); return 0; }
3. 问题
上面代码的运行结果第三个输出是在第二个输出的基础上加了30分钟。为什么tmp_time变化会导致*ptime的变化。
另外#include和#include也有区别。