檢視原始碼 日曆 行為 (Elixir v1.16.2)
此模組定義在 Elixir 中使用日曆、日期、時間和日期時間時應負的責任。
它定義 Elixir 中日曆行為的類型和最小實作。Elixir 中日曆功能的目標是提供一個可互通性的基礎,而非一個功能齊全的日期時間 API。
有關實際的日期、時間和日期時間結構,請參閱 Date
、Time
、NaiveDateTime
和 DateTime
。
年份、月份、日期等類型為過度指定。例如,month/0
類型指定為整數,而非 1..12
。這是因為不同的日曆每個月可能會有不同的天數。
摘要
類型
日曆實作。
包含日期欄位的任何對應或結構。
包含日期時間欄位的任何對應或結構。
在日曆之間轉換時,使用內部時間格式。
表示 day
和 era
的元組。
在日曆之間轉換時,使用的內部日期格式。
具有儲存精度的微秒。
包含未精確日期時間欄位的任何對應或結構。
時區標準偏移量(以秒為單位,在夏令時間通常不為零)。
包含時間欄位的任何映射或結構。
根據 IANA tz 資料庫的時間區域 ID(例如,Europe/Zurich
)。
指定日曆運算的時間區域資料庫。
標準時間的時間區域 UTC 偏移(以秒為單位)。
時間區域縮寫(例如,CET
或 CEST
或 BST
)。
回呼函式
根據日曆將日期轉換為字串。
根據日曆將日期時間(含時區)轉換為字串。
根據指定的 year
、month
和 day
計算日和紀元。
根據指定的 year
、month
和 day
計算星期幾。
根據指定的 year
、month
和 day
計算一年中的第幾天。
定義日曆的翻轉時刻。
傳回指定年份中指定月份的天數。
將指定的 iso_days/0
轉換為一天的第一時刻。
將指定的 iso_days/0
轉換為一天的最後時刻。
如果指定的年份是閏年,則傳回 true
。
傳回指定年份中的月份數。
將 iso_days/0
轉換為日曆的日期時間格式。
將日期時間(不含時區)轉換為 iso_days/0
格式。
根據日曆將未指定時區的日期時間(不含時區)轉換為字串。
將 date_to_string/3
傳回的日期字串表示法剖析為日期組。
將 naive_datetime_to_string/7
傳回的樸素日期時間字串表示解析成樸素日期時間組。
將 time_to_string/4
傳回的時間字串表示解析成時間組。
將 datetime_to_string/11
傳回的日期時間字串表示解析成日期時間組。
根據指定的 year
、month
和 day
計算該年的季度。
將 day_fraction/0
轉換成日曆的時間格式。
根據日曆將時間轉換成字串。
如果指定的日期描述日曆中的適當日期,應傳回 true
。
如果指定的時間描述日曆中的適當時間,應傳回 true
。
根據指定的 year
計算年和年代。
函式
如果兩個日曆開始新一天的時刻相同,則傳回 true
,否則傳回 false
。
取得目前的時區資料庫。
設定目前的時區資料庫。
將指定的日期、時間或日期時間格式化成字串。
傳回截斷為指定精確度 (:microsecond
、:millisecond
或 :second
) 的微秒組。
類型
@type calendar() :: module()
日曆實作。
@type date() :: %{ optional(any()) => any(), calendar: calendar(), year: year(), month: month(), day: day() }
包含日期欄位的任何對應或結構。
@type datetime() :: %{ optional(any()) => any(), calendar: calendar(), year: year(), month: month(), day: day(), hour: hour(), minute: minute(), second: second(), microsecond: microsecond(), time_zone: time_zone(), zone_abbr: zone_abbr(), utc_offset: utc_offset(), std_offset: std_offset() }
包含日期時間欄位的任何對應或結構。
@type day() :: pos_integer()
@type day_fraction() :: {parts_in_day :: non_neg_integer(), parts_per_day :: pos_integer()}
在日曆之間轉換時,使用內部時間格式。
它表示一天的時間(從午夜開始)的一部分。 parts_in_day
指定一天已經過去了多少,而 parts_per_day
表示一天中有多少部分。
@type day_of_era() :: {day :: non_neg_integer(), era()}
表示 day
和 era
的元組。
@type day_of_week() :: non_neg_integer()
@type era() :: non_neg_integer()
@type hour() :: non_neg_integer()
@type iso_days() :: {days :: integer(), day_fraction()}
在日曆之間轉換時,使用的內部日期格式。
這是自 ISO 8601 表示法中 0000-01-01+00:00T00:00.000000
(也稱為前儒略曆的 公元前 1 年 1 月 1 日午夜)以來已過的天數,包括最後一天已過的小數部分。
@type microsecond() :: {value :: non_neg_integer(), precision :: non_neg_integer()}
具有儲存精度的微秒。
精度表示在以外部格式表示微秒時必須使用的位數。如果精度為 0
,表示必須略過微秒。
@type minute() :: non_neg_integer()
@type month() :: pos_integer()
@type naive_datetime() :: %{ optional(any()) => any(), calendar: calendar(), year: year(), month: month(), day: day(), hour: hour(), minute: minute(), second: second(), microsecond: microsecond() }
包含未精確日期時間欄位的任何對應或結構。
@type second() :: non_neg_integer()
@type std_offset() :: integer()
時區標準偏移量(以秒為單位,在夏令時間通常不為零)。
必須將其新增到 utc_offset/0
以獲得用於「牆上時間」的 UTC 總偏移量。
@type time() :: %{ optional(any()) => any(), hour: hour(), minute: minute(), second: second(), microsecond: microsecond() }
包含時間欄位的任何映射或結構。
@type time_zone() :: String.t()
根據 IANA tz 資料庫的時間區域 ID(例如,Europe/Zurich
)。
@type time_zone_database() :: module()
指定日曆運算的時間區域資料庫。
DateTime
模組中的許多函式需要時區資料庫。預設情況下,此模組使用 Calendar.get_time_zone_database/0
傳回的預設時區資料庫,預設為 Calendar.UTCOnlyTimeZoneDatabase
。此資料庫僅處理 Etc/UTC
日期時間,並對任何其他時區傳回 {:error, :utc_only_time_zone_database}
。
其他時區資料庫(包括套件提供的資料庫)可以透過設定檔設定為預設值
config :elixir, :time_zone_database, CustomTimeZoneDatabase
或呼叫 Calendar.put_time_zone_database/1
。
請參閱 Calendar.TimeZoneDatabase
以取得有關自訂時區資料庫的更多資訊。
@type utc_offset() :: integer()
標準時間的時間區域 UTC 偏移(以秒為單位)。
另請參閱 std_offset/0
。
@type week() :: pos_integer()
@type year() :: integer()
@type zone_abbr() :: String.t()
時間區域縮寫(例如,CET
或 CEST
或 BST
)。
回呼
根據日曆將日期轉換為字串。
datetime_to_string( year, month, day, hour, minute, second, microsecond, time_zone, zone_abbr, utc_offset, std_offset )
檢視原始碼@callback datetime_to_string( year(), month(), day(), hour(), minute(), second(), microsecond(), time_zone(), zone_abbr(), utc_offset(), std_offset() ) :: String.t()
根據日曆將日期時間(含時區)轉換為字串。
@callback day_of_era(year(), month(), day()) :: day_of_era()
根據指定的 year
、month
和 day
計算日和紀元。
@callback day_of_week(year(), month(), day(), starting_on :: :default | atom()) :: {day_of_week(), first_day_of_week :: non_neg_integer(), last_day_of_week :: non_neg_integer()}
根據指定的 year
、month
和 day
計算星期幾。
starting_on
表示該週的第一天。所有日曆都必須至少支援 :default
值。它們也可能支援表示其星期數的其他值。
@callback day_of_year(year(), month(), day()) :: non_neg_integer()
根據指定的 year
、month
和 day
計算一年中的第幾天。
@callback day_rollover_relative_to_midnight_utc() :: day_fraction()
定義日曆的翻轉時刻。
在您的日曆中,這是當前日期結束且下一天開始的時刻。
此函式的結果用於檢查兩個日曆是否在一天中的同一時間換日。如果沒有,我們只能在它們之間轉換日期時間和時間。如果有的話,表示我們也可以在它們之間轉換日期以及未指定時區的日期時間。
此日部分應以其最簡化的形式呈現,以加快比較速度。
範例
- 如果在你的日曆中,新的一天從午夜開始,傳回
{0, 1}
。 - 如果在你的日曆中,新的一天從日出開始,傳回
{1, 4}
。 - 如果在你的日曆中,新的一天從中午開始,傳回
{1, 2}
。 - 如果在你的日曆中,新的一天從日落開始,傳回
{3, 4}
。
傳回指定年份中指定月份的天數。
將指定的 iso_days/0
轉換為一天的第一時刻。
將指定的 iso_days/0
轉換為一天的最後時刻。
如果指定的年份是閏年,則傳回 true
。
閏年是比正常年份更長的一年。確切的意義取決於日曆。如果日曆不支援閏年的概念,則必須傳回 false
。
傳回指定年份中的月份數。
@callback naive_datetime_from_iso_days(iso_days()) :: {year(), month(), day(), hour(), minute(), second(), microsecond()}
將 iso_days/0
轉換為日曆的日期時間格式。
@callback naive_datetime_to_iso_days( year(), month(), day(), hour(), minute(), second(), microsecond() ) :: iso_days()
將日期時間(不含時區)轉換為 iso_days/0
格式。
@callback naive_datetime_to_string( year(), month(), day(), hour(), minute(), second(), microsecond() ) :: String.t()
根據日曆將未指定時區的日期時間(不含時區)轉換為字串。
將 date_to_string/3
傳回的日期字串表示法剖析為日期組。
@callback parse_naive_datetime(String.t()) :: {:ok, {year(), month(), day(), hour(), minute(), second(), microsecond()}} | {:error, atom()}
將 naive_datetime_to_string/7
傳回的樸素日期時間字串表示解析成樸素日期時間組。
給定的字串可能包含時區偏移,但會被忽略。
@callback parse_time(String.t()) :: {:ok, {hour(), minute(), second(), microsecond()}} | {:error, atom()}
將 time_to_string/4
傳回的時間字串表示解析成時間組。
@callback parse_utc_datetime(String.t()) :: {:ok, {year(), month(), day(), hour(), minute(), second(), microsecond()}, utc_offset()} | {:error, atom()}
將 datetime_to_string/11
傳回的日期時間字串表示解析成日期時間組。
傳回的日期時間必須為 UTC。原始撰寫的 utc_offset
必須在結果中傳回。
@callback quarter_of_year(year(), month(), day()) :: non_neg_integer()
根據指定的 year
、month
和 day
計算該年的季度。
@callback time_from_day_fraction(day_fraction()) :: {hour(), minute(), second(), microsecond()}
將 day_fraction/0
轉換成日曆的時間格式。
@callback time_to_day_fraction(hour(), minute(), second(), microsecond()) :: day_fraction()
將指定的時間轉換成 day_fraction/0
格式。
@callback time_to_string(hour(), minute(), second(), microsecond()) :: String.t()
根據日曆將時間轉換成字串。
如果指定的日期描述日曆中的適當日期,應傳回 true
。
@callback valid_time?(hour(), minute(), second(), microsecond()) :: boolean()
如果指定的時間描述日曆中的適當時間,應傳回 true
。
根據指定的 year
計算年和年代。
函式
如果兩個日曆開始新一天的時刻相同,則傳回 true
,否則傳回 false
。
如果兩個日曆不相容,我們只能在它們之間轉換日期時間和時間。如果它們相容,表示我們也可以在它們之間轉換日期以及未指定時區的日期時間。
@spec get_time_zone_database() :: time_zone_database()
取得目前的時區資料庫。
@spec put_time_zone_database(time_zone_database()) :: :ok
設定目前的時區資料庫。
將指定的日期、時間或日期時間格式化成字串。
日期時間可以是任何 Calendar
類型(Time
、Date
、NaiveDateTime
和 DateTime
)或任何地圖,只要它們包含格式化所需的所有相關欄位即可。例如,如果你使用 %Y
來格式化年份,則日期時間必須有 :year
欄位。因此,如果你傳遞 Time
或沒有 :year
欄位的映射給預期 %Y
的格式,將會引發錯誤。
常見用法的範例
iex> Calendar.strftime(~U[2019-08-26 13:52:06.0Z], "%y-%m-%d %I:%M:%S %p")
"19-08-26 01:52:06 PM"
iex> Calendar.strftime(~U[2019-08-26 13:52:06.0Z], "%a, %B %d %Y")
"Mon, August 26 2019"
使用者選項
:preferred_datetime
- 顯示日期時間的首選格式字串,它不能包含%c
格式,如果未收到選項,則預設為"%Y-%m-%d %H:%M:%S"
:preferred_date
- 顯示日期的首選格式字串,它不能包含%x
格式,如果未收到選項,則預設為"%Y-%m-%d"
:preferred_time
- 顯示時間的首選格式字串,它不能包含%X
格式,如果未收到選項,則預設為"%H:%M:%S"
:am_pm_names
- 接收:am
或:pm
並傳回一天中時段名稱的函式,如果未收到選項,則預設為傳回"am"
和"pm"
的函式:month_names
- 接收數字並傳回對應月份名稱的函式,如果未收到選項,則預設為傳回英文月份名稱的函式:abbreviated_month_names
- 接收數字並傳回對應月份簡稱的函式,如果未收到選項,則預設為傳回英文月份簡稱的函式:day_of_week_names
- 接收數字並傳回對應星期名稱的函式,如果未收到選項,則預設為傳回英文星期名稱的函式:abbreviated_day_of_week_names
- 一個接收數字並傳回對應星期縮寫名稱的函數,如果未收到選項,它預設為傳回英文星期縮寫名稱的函數
格式化語法
string_format
參數的格式化語法是以下格式的字元序列
%<padding><width><format>
其中
%
: 表示格式化區段的開始<padding>
: 設定內距 (見下方)<width>
: 表示格式化區段最小大小的數字<format>
: 格式本身 (見下方)
可接受的內距選項
-
: 沒有內距,從格式中移除所有內距_
: 以空格填滿內距0
: 以零填滿內距
可接受的字串格式
string_format
可接受的格式為
格式 | 說明 | 範例 (ISO) |
---|---|---|
a | 星期的縮寫名稱 | 一 |
A | 星期的完整名稱 | 星期一 |
b | 月份的縮寫名稱 | 1 月 |
B | 月份的完整名稱 | 一月 |
c | 首選的日期+時間表示法 | 2018-10-17 12:34:56 |
d | 一個月中的第幾天 | 01, 31 |
f | 微秒 (不支援寬度和內距修改器) | 000000, 999999, 0123 |
H | 使用 24 小時制的時 | 00, 23 |
I | 使用 12 小時制的時 | 01, 12 |
j | 一年中的第幾天 | 001, 366 |
m | 月份 | 01, 12 |
M | 分鐘 | 00, 59 |
p | "AM" 或 "PM" (中午為 "PM",午夜為 "AM") | 上午, 下午 |
P | "am" 或 "pm" (中午為 "pm",午夜為 "am") | 上午, 下午 |
q | 季度 | 1, 2, 3, 4 |
s | 自紀元時間 (1970-01-01 00:00:00+0000 (UTC)) 以來的秒數 | 1565888877 |
S | 秒 | 00, 59, 60 |
u | 星期幾 | 1(星期一),7(星期日) |
x | 首選日期(不含時間)表示法 | 2018-10-17 |
X | 首選時間(不含日期)表示法 | 12:34:56 |
y | 2 位數年份 | 01, 01, 86, 18 |
Y | 年份 | -0001, 0001, 1986 |
z | UTC 的時區偏移量 +hhmm/-hhmm(如果為原始時間,則為空字串) | +0300, -0530 |
Z | 時區縮寫(如果為原始時間,則為空字串) | CET、BRST |
% | 文字「%」 | % |
任何其他字元都將被解釋為無效格式,並會引發錯誤。
範例
沒有使用者選項
iex> Calendar.strftime(~U[2019-08-26 13:52:06.0Z], "%y-%m-%d %I:%M:%S %p")
"19-08-26 01:52:06 PM"
iex> Calendar.strftime(~U[2019-08-26 13:52:06.0Z], "%a, %B %d %Y")
"Mon, August 26 2019"
iex> Calendar.strftime(~U[2020-04-02 13:52:06.0Z], "%B %-d, %Y")
"April 2, 2020"
iex> Calendar.strftime(~U[2019-08-26 13:52:06.0Z], "%c")
"2019-08-26 13:52:06"
有使用者選項
iex> Calendar.strftime(~U[2019-08-26 13:52:06.0Z], "%c", preferred_datetime: "%H:%M:%S %d-%m-%y")
"13:52:06 26-08-19"
iex> Calendar.strftime(
...> ~U[2019-08-26 13:52:06.0Z],
...> "%A",
...> day_of_week_names: fn day_of_week ->
...> {"segunda-feira", "terça-feira", "quarta-feira", "quinta-feira",
...> "sexta-feira", "sábado", "domingo"}
...> |> elem(day_of_week - 1)
...> end
...>)
"segunda-feira"
iex> Calendar.strftime(
...> ~U[2019-08-26 13:52:06.0Z],
...> "%B",
...> month_names: fn month ->
...> {"січень", "лютий", "березень", "квітень", "травень", "червень",
...> "липень", "серпень", "вересень", "жовтень", "листопад", "грудень"}
...> |> elem(month - 1)
...> end
...>)
"серпень"
@spec truncate(microsecond(), :microsecond | :millisecond | :second) :: microsecond()
傳回截斷為指定精確度 (:microsecond
、:millisecond
或 :second
) 的微秒組。