Col*_*Row 2 postgresql query date-format date date-math
timestamp我用一列来指示一行是在白天还是晚上创建的。我的代码如下,但由于某种原因,我只得到“DAY”作为结果。我没有正确格式化值吗?
select record_id, rec_date,
case when date_part('hour', rec_date) between 20 and 07 then 'Night'
else 'Day' end as Indicator
from records;
Run Code Online (Sandbox Code Playgroud)
该rec_date列是一个时间戳,我可以在其中看到诸如2019-11-20 21:34:02.000000- 之类的值,它应该得到一个'Night'指标。
Erw*_*ter 10
SELECT record_id, rec_date
, CASE WHEN rec_date::time < '08:00' THEN 'Night'
WHEN rec_date::time >= '20:00' THEN 'Night'
ELSE 'Day' END AS indicator
FROM records;
Run Code Online (Sandbox Code Playgroud)
这是date-math而不是date-format 的问题。您想正确有效地进行数学运算。'Day' 和 'Night' 的格式没有问题。
McNets 已经阐明了BETWEEN对BETWEEN SYMMETRIC. 但BETWEEN SYMMETRIC 20 AND 07最终仍然会变得丑陋、缓慢和不正确。
SYMMETRIC仅对参数化边界才有意义,在这种情况下,您不知道哪个会提前更大。不是这样,20而且07是常数。
天真地应用于您的案例,您会日夜颠倒,因为BETWEEN SYMMETRIC 20 AND 07最终被评估为BETWEEN 07 AND 20(只是更昂贵)。
好的,通过切换“白天”和“夜晚”轻松解决。但是现在,时间 20:** 和 07:** 将被标记为“Day”。BETWEEN,带或不带SYMMETRIC,包括上限和下限。这就是为什么它几乎总是与时间戳一起使用的错误工具。在这种特殊情况下,date_part()碰巧在某种程度上解决了包含两个边界的内置问题。无论哪种方式,为了符合您的原始意图,它必须是:
CASE WHEN date_part('hour', ts) BETWEEN '08' AND '19' -- adjusted
THEN 'Day' ELSE 'Night' END AS indicator
Run Code Online (Sandbox Code Playgroud)带有表达式的查询的成本date_part('hour', rec_date) BETWEEN SYMMETRIC 20 AND 07大约是我建议的两倍。较大的部分由于无意义,较小的部分由于功能比演员更昂贵。SYMMETRIC
建议的表达方式比曲折的表达方式更不容易被误解BETWEEN,因为它清楚地表明了哪些边界被包括在内。
我不会将时间戳列称为“record_date”,因为它date是与timestamp. 更容易混淆。
如果您的实际数据类型恰好是timestamptz(或可能的话,在任何情况下),你可能需要定义,其中世界它应该是“天”或“空中飞人”。看:
| 归档时间: |
|
| 查看次数: |
784 次 |
| 最近记录: |