libc中的時間函數

下面看一下localtime, gmtime,mktime的實現

如下圖所示:localtime和gmtime共同使用全局內存_tmbuf存入計算的結果。所以多線程要避免使用這兩個函數。__tz_convert依次調用tzset_internal(也是tzset的調用方法,用於從環境變量和文件中獲取時區信息),__offtime計算時間。

 

image.pngimage.png(圖中函數簽名是一種老的c風格,先列出函數參數,然後再指定它們的類型)

tzset_internal函數:此函數首先獲取tz = getenv ("TZ"),若TZ爲NULL則將tz賦值爲localtime;然後調用__tzfile_read (tz, 0, NULL);該函數將tz拼接到tzdir = getenv ("TZDIR")路徑後面組成一個完整的文件名,接着讀取此文件中的時區信息。若TZ不是一個有效的時區文件(如TZ='GMT-8'),則文件讀取會失敗。此時就會對TZ進行如下解析:1)跳過字符串到+-號的位置(左圖);2)對後面數值處理。需要注意的是GMT-8的‘-’對offset的影響是+數。

最後這個函數修改全局變量timezone的值:__timezone = -tz_rules[0].offset;  timezone的符號與”GMT-8“的符號一致

image.pngimage.png

 

 __offtime函數:

左邊是__offtime在__tz_convert中被調用的實參情況,剛計算的offset傳入進去。右邊的圖中顯示這個offset被加到t上!!

image.pngimage.png

總上得出:

1)日曆時 + 時區 = 本地時間       (日曆時就是time函數的輸出值,是從1970年1月1日起的一個絕對時間)

2)涉及文件操作,頻繁變動時區會影響性能

mktime函數:

此函數的入參是本地時間,返回值是日曆時。此函數還會校正輸入的本地時間。

此函數做這樣的運算:日曆時 = 本地時間 - 時區

 

附: 全球劃分24個時區,東西半球各12個時區,東爲正(GMT-1...GMT-12),表現爲比格林尼治早,西爲負(GMT+1...GMT+12)。GMT後面的符號決定日曆時和時區的加減,後面的數字無謂大小(可以設置GMT-22,這是沒有約束的);我們必須自我約束數字的大小和符號,不然就會破壞約定,得不到正確的時間。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章