理想情況下,我希望能夠做的是取一個時區的名稱並調用一個函數來請求相應的時區信息(從UTC偏移,DST偏移量,DST開關的日期等)在Linux中。但是,我找不到任何方法來做到這一點。這些信息存在於/usr/share/zoneinfo/
那裏的各種二進制文件中,但我不知道如何閱讀它們,或者是否有辦法讓操作系統向您提供其中的信息,而不必自己閱讀它們。所以,我正在尋找獲取這些信息的方法。理想情況下,將會有一個posix函數爲你做這個工作,這樣它就可以在Linux以外的POSIX系統上工作,但如果沒有,我至少想知道正確的方法(或者至少是最好的方式)在Linux中獲取任意時區的時區信息。如何獲取Linux/POSIX中任意時區的信息?
回答
的tzcode package(在ftp://ftp.iana.org/tz/releases與數據一起找到)包含用於直接與該數據工作tzfile格式的具有報頭文件tzfile.h
沿的描述。
沒有一個標準的方法來做到這一點。你可以看看ICU。它聲稱:
格式:根據所選語言環境的約定格式化數字,日期,時間和貨幣金額。這包括將月份和日期名稱翻譯成所選語言,選擇適當的縮寫,正確排序字段等。此數據也來自Common Locale Data Repository。
時間計算:在傳統的公曆日曆之外提供了多種類型的日曆。 提供了一套完整的時區計算API(強調增加了)。
舊問題的新答案。
新答案的依據:現在有一個modern, free, open-source, C++11/14/17 library可以做到這一點。 它確實需要一些installation。但它可以跨Linux/macOS/Windows移植。它有full documentation,甚至有video introduction。
以下是獲取有關特定時區信息的示例程序。我僅以自己的時區爲例。該庫支持全IANA timezone database:
#include "tz.h"
#include <iostream>
int
main()
{
auto zone = date::locate_zone("America/New_York");
std::cout << *zone << '\n';
std::cout << zone->get_info(std::chrono::system_clock::now()) << '\n';
}
第一行通過其IANA名稱查找數據庫。
auto zone = date::locate_zone("America/New_York");
返回類型是date::time_zone const*
。這個功能永遠不會返回nullptr
,儘管如果它不能找到時區時會拋出(具有極好的what()
)。
第二行打印出時間段的定義:
std::cout << *zone << '\n';
這條線的輸出不是非常有用到該庫的客戶端。它主要是有用的,以自己在調試庫:
America/New_York -04:56:02 LMT 1883 Nov/18 12:03:58 1883-11-18 17:00:00 UTC 1883-11-18 12:03:58 STD 1883-11-18 12:03:58 00:00 {nullptr, -32768} {nullptr, 32767}
-05:00:00 US E%sT 1920 Jan/01 00:00:00 1920-01-01 05:00:00 UTC 1920-01-01 00:00:00 STD 1920-01-01 00:00:00 00:00 S {US 1918 1919 Mar/Sun[last] 02:00:00 01:00 D, 1918} {US 1918 1919 Oct/Sun[last] 02:00:00 00:00 S, 1919}
-05:00:00 NYC E%sT 1942 Jan/01 00:00:00 1942-01-01 05:00:00 UTC 1942-01-01 00:00:00 STD 1942-01-01 00:00:00 00:00 S {NYC 1920 1920 Mar/28 02:00:00 01:00 D, 1920} {NYC 1921 1954 Sep/Sun[last] 02:00:00 00:00 S, 1941}
-05:00:00 US E%sT 1946 Jan/01 00:00:00 1946-01-01 05:00:00 UTC 1946-01-01 00:00:00 STD 1946-01-01 00:00:00 00:00 S {US 1942 1942 Feb/09 02:00:00 01:00 W, 1942} {US 1945 1945 Sep/30 02:00:00 00:00 S, 1945}
-05:00:00 NYC E%sT 1967 Jan/01 00:00:00 1967-01-01 05:00:00 UTC 1967-01-01 00:00:00 STD 1967-01-01 00:00:00 00:00 S {NYC 1921 1954 Apr/Sun[last] 02:00:00 01:00 D, 1946} {NYC 1955 1966 Oct/Sun[last] 02:00:00 00:00 S, 1966}
-05:00:00 US E%sT 32767 Dec/31 00:00:00UTC 32767-12-31 00:00:00 UTC 32767-12-30 19:00:00 STD 32767-12-30 19:00:00 00:00 S {US 1967 1973 Apr/Sun[last] 02:00:00 01:00 D, 1967} {US 2007 32767 Nov/Sun[1] 02:00:00 00:00 S, 32767}
不過的原因,我表示此行是一家以說明詢問了關於時區的信息,而無需還提供一個時間點,是不太可能向您提供您正在尋找的信息。有關時區的信息本身是時間的函數,包括偏移量,夏令細節,縮寫,等等
最後一行:
std::cout << zone->get_info(std::chrono::system_clock::now()) << '\n';
很可能是最有幫助的。這個返回集合sys_info
看起來像這樣:
struct sys_info
{
sys_seconds begin;
sys_seconds end;
std::chrono::seconds offset;
std::chrono::minutes save;
std::string abbrev;
};
這只是對我輸出:
2016-11-06 06:00:00
2017-03-12 07:00:00
-05:00:00
00:00
EST
這意味着:
- 此信息有效期爲2016年11月6日06 :00:00 UTC直到(但不包括)2017-03-12 07:00:00 UTC。
- 此時間段的UTC偏移量爲-5小時。
- 這不被視爲夏令時期(save == 00:00)。
- 這段時間的縮寫是EST。
當然,您可以在程序中訪問此聚合的字段,而不是將它們打印出來。
如果你想看到這樣的結果可能是什麼樣子6個月現在:
std::cout << zone->get_info(std::chrono::system_clock::now() + date::months{6}) << '\n';
目前輸出:
2017-03-12 07:00:00
2017-11-05 06:00:00
-04:00:00
01:00
EDT
這一切被認爲是在這個低級別的訪問圖書館。存在更高級別的API,因此您不必處理低級別的概念,例如當前的UTC偏移量。低層次的東西是存在的,如果你需要它(沒有隱藏),但沒有必要爲常見的使用情況,例如獲取當前時間在任何特定的時間段:
using namespace date;
using namespace std::chrono;
std::cout << make_zoned("America/New_York", system_clock::now()) << '\n';
這只是我的輸出:
2017-03-07 19:26:53.711662 EST
在C++ 17時,由於模板扣除指南,上面的線將不再需要「做工廠函數」扣除用途:
std::cout << zoned_time{"America/New_York", system_clock::now()} << '\n';
zoned_time
是一個班級模板,以持續時間爲模板,並由chrono::time_point
(第二個參數 - 在本例中爲microseconds
)的chrono::duration
推導出來。
這是一個全功能的日期/時間/時區庫,既有低級訪問,也有高級抽象(正如C++的哲學)。正確性和類型安全性在這個圖書館中是非常重要的。它是C++ 11中引入的<chrono>
庫的擴展,不是替代品。
免責聲明:我是這個庫的主要作者,雖然有很多的貢獻者(對此我很感激)。
- 1. 如何獲取Windows中任意時區的信息?
- 2. 獲取VBA中的時區信息(Excel)
- 3. Swift:從UITapGestureRecognizer獲取任意信息
- 4. 在Outlook中獲取時區信息
- 5. 如何在Java中使用OS X獲取時區信息?
- 6. 如何使用Twilio獲取SMS的時區信息?
- 7. Report Builder 2.0:如何獲取正確的時區信息
- 8. 如何獲取Light Table工作區中的目錄信息?
- 9. 如何獲取Android中的國家/地區信息?
- 10. asp.net任意用戶信息
- 11. 如何獲取.net中的cpu信息?
- 12. 從matlab中的圖像中的任何對象獲取信息
- 13. 如何查看我的時區信息
- 14. Android - 如何獲取動態意圖的包詳細信息
- 15. 如何在包裝任意函數時保留類型信息
- 16. 如何獲取Twitter用戶社區的最新推文信息,
- 17. 如何獲取巴哈馬的地區和文化信息?
- 18. 獲取分區和卷信息
- 19. 如何從java applet中獲取信息?
- 20. 如何在Silverlight中獲取GC信息?
- 21. 如何從圖像中獲取信息?
- 22. 如何從標準中獲取信息?
- 23. 如何從子表中獲取信息
- 24. 使用mod_plsql時無法獲取時區信息?
- 25. 如何從SVN信息庫中獲取信息?
- 26. .NET時區信息
- 27. 如何從Android的任何時區獲取具體時間?
- 28. 如何從另一個意圖獲取信息?
- 29. 獲取信息
- 30. 在iPhone上獲取時區信息的座標
ICU確實有適當的日曆實施./ – 2012-10-11 17:18:54