CodeGym /课程 /SQL SELF /处理时间区间:INTERVAL

处理时间区间:INTERVAL

SQL SELF
第 31 级 , 课程 4
可用

健身训练要一个半小时,上班一天8小时,休息20分钟,煮鸡蛋10分钟。这些都是时间区间的例子。

时间区间在实际开发里超有用,比如你要算任务截止时间、搞清楚两个日期差多少、或者加减点时间啥的。但在深入之前,先简单回顾下我们上节课讲到哪儿了。

在PostgreSQL里,INTERVAL是专门用来表示一段时间的数据类型。和其他时间类型不一样,它不存具体的日期或时间,而是描述一个区间,比如:"2天"、"3小时"、"5分钟"。

INTERVAL的语法

区间可以这样写:

INTERVAL '数字 时间单位'

举几个例子:

INTERVAL '2 days' -- 两天
INTERVAL '3 hours' -- 三小时
INTERVAL '15 minutes' -- 十五分钟
INTERVAL '1 day 2 hours' -- 一天两小时

PostgreSQL支持各种时间单位:yearmonthdayhourminutesecond。你可以在一个表达式里随便组合。

在查询里用INTERVAL

INTERVAL数据类型和其他时间类型(DATETIMESTAMP)一起用的时候特别爽。下面是常见的操作。

给日期/时间加上区间

你可以把区间加到日期或时间上。比如:

SELECT CURRENT_DATE + INTERVAL '7 days' AS delivery_date;
-- 得到7天后的日期

结果:

delivery_date
2023-10-08

从日期/时间里减去区间

除了加,还能减:

SELECT NOW() - INTERVAL '2 hours' AS two_hours_ago;
-- 得到两小时前的时间

结果:

two_hours_ago
2023-10-01 10:00:00.000

计算两个日期的差值

INTERVAL很强大的一点就是能直接算两个日期的差:

SELECT '2023-10-15'::DATE - '2023-10-01'::DATE AS days_difference;
-- 两个日期之间差几天

结果:

days_difference
14 days

注意,这里结果也是一个时间区间。

INTERVAL的实用例子

算送货日期。 假设有个网店,送货要3到7天。可以这样算可能的送货日期:

SELECT CURRENT_DATE + INTERVAL '3 days' AS earliest_delivery,
       CURRENT_DATE + INTERVAL '7 days' AS latest_delivery;

结果:

earliest_delivery latest_delivery
2023-10-04 2023-10-08

统计任务完成时间。 比如有个tasks表,每个任务有个开始时间。要算任务结束时间(按小时算):

CREATE TABLE tasks (
    task_id SERIAL PRIMARY KEY,
    task_name TEXT,
    start_time TIMESTAMP,
    duration INTERVAL
);

INSERT INTO tasks (task_name, start_time, duration)
VALUES
('准备报告', '2023-10-01 09:00:00', INTERVAL '4 hours'),
('测试应用', '2023-10-01 10:00:00', INTERVAL '2 hours 30 minutes');

SELECT task_name,
       start_time,
       start_time + duration AS end_time
FROM tasks;

结果:

task_name start_time end_time
准备报告 2023-10-01 09:00:00 2023-10-01 13:00:00
测试应用 2023-10-01 10:00:00 2023-10-01 12:30:00

比较任务耗时。 有时候我们想找出所有耗时少于3小时的任务:

SELECT task_name
FROM tasks
WHERE duration < INTERVAL '3 hours';

结果:

task_name
测试应用

INTERVAL的一些小技巧

动态计算区间。 可以把区间和别的操作结合起来。比如,把某个字段里的天数转成区间:

SELECT CURRENT_DATE + (order_days || ' days')::INTERVAL AS order_due_date
FROM orders;

把区间转成字符串。 有时候你想把区间转成字符串显示:

SELECT INTERVAL '2 days 3 hours'::TEXT AS interval_text;

结果:

interval_text
2 days 03:00:00

用INTERVAL常见的坑

虽然INTERVAL很强大,但用的时候也容易踩坑。最常见的就是格式写错。比如你写INTERVAL '2 hours and 30 minutes',PostgreSQL会报错,因为它不认识"and"。正确写法是:INTERVAL '2 hours 30 minutes'

还有一种错法是忘了写时间单位,比如INTERVAL '2'。PostgreSQL不知道你这"2"是啥,所以一定要写清楚单位(2 days2 hours)。

1
调查/小测验
日期和时间的操作第 31 级,课程 4
不可用
日期和时间的操作
日期和时间的操作
评论
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION