电子说
一、先从结构体看起
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()为负。*/
};
月份为0-11
年份又是从1900年开始
星期又是0~6
time_t
time_t却是从1970/1/1 000开始的秒数
二、再从重点转换函数看起
timegm()和gmtime_r()
timegm()是将struct tm结构体转换为time_t,直接时间计算
gmtime_r()是将time_t转换为struct tm结构体数据
mktime()和localtime_r()
mktime先调用timegm()转换为time_t,再减去时区
localtime_r()先加上时区值,再调用gmtime_r()转换为结构体
三、再谈time格式化字符:
ctime(),ctime_r(),asctime()最终都是调用asctime_r()
四、再从底层驱动看起,
1.实际的硬件时间:
-# 实际年份-1900年-100的年份 = 实际年份-2000年,
-# 其他时间为本地时分秒
相当于本地时间:2023/11/23 19:03:00 实际存储到硬件为23/11/23 19:03:00
在网上搜到一篇文章,就说的windows和linux系统硬件存储的实际时间也是本地时间
五、硬件时间转换与timestamp相互转换
在get_rtc_timestamp中mktime()将底层硬件时间(带时区)转换为相对1970/1/1 000的秒数(不带时区),
重点:mktime()将struct tm * t结构时间减去时区值
在set_rtc_time_stamp中localtime()将相对1970/0/0 000的秒数(不带时区)转换为struct tm结构体数据(带时区)
六、time()和stime函数
time()调用_control_rtc()→最终调用get_rtc_timestamp()
stime函数调用_control_rtc()→最终调用set_rtc_timestamp()
总结:
底层硬件时间与tm结构体时间都是有区别,各处应使用tm结构体时间(应为1900年到现在的时间)
全部0条评论
快来发表一下你的评论吧 !