阅读(3735) (12)

PostgreSQL 处理无效或不明确的时间戳

2021-08-24 15:07:42 更新

通常,如果日期/时间字符串在语法上有效但包含 超出范围的字段值,将引发错误。 例如,输入2月31日将被拒绝。

在夏令时转换期间,看似有效的时间戳字符串可能表示不存在或不明确的时间戳。 这样的输入不会被拒绝;不确定性可以通过要应用哪个UTC偏移来解决。 例如,假设TimeZone参数设置为America/New_York,请考虑

=> SELECT '2018-03-11 02:30'::timestamptz;
      timestamptz
------------------------
 2018-03-11 03:30:00-04
(1 row)

因为那天是那个时区的春天过渡日期,所以没有民用时间凌晨2:30; 时钟从2AM EST跳转到3AM EDT。 PostgreSQL将给定时间解释为标准时间(UTC-5),然后呈现为3:30AM EDT(UTC-4)。

相反,请考虑后向过渡期间的行为:

=> SELECT '2018-11-04 02:30'::timestamptz;
      timestamptz
------------------------
 2018-11-04 02:30:00-05
(1 row)

在那一天,上午2:30有两种可能的解释; 2:30AM EDT,以及一小时以后,如果转换到标准时间,即2:30AM EST。 同样,PostgreSQL将给定时间解释为标准时间(UTC-5)。 我们可以通过指定夏令时来强行控制:

=> SELECT '2018-11-04 02:30 EDT'::timestamptz;
      timestamptz
------------------------
 2018-11-04 01:30:00-05
(1 row)

此时间戳可以有效地呈现为2:30 UTC-4或1:30 UTC-5; 时间戳输出代码选择后者。

在这些情况下应用的精确规则是,出现在前向跳转的夏令时转换中的无效时间戳被分配了转换之前的时区对应的UTC偏移; 可能落在后向跳转的两边的不确定的时间戳被分配了转换之后的时区对应的UTC偏移。 在大多数时区,这相当于说在有疑问时,标准时间解释是首选

在所有情况下,可以显式使用数字UTC偏移或对应于固定UTC偏移的时区缩写明确指定与时间戳关联的UTC偏移。 刚刚给出的规则仅在需要推断偏移量变化的时区的UTC偏移时才适用。