DAY_CEIL
描述
DAY_CEIL 函数用于将指定的日期或时间值向上取整(ceil)到最近的指定天数周期的起点。即返回不小于输入日期时间的最小周期时刻,周期规则由 period(周期天数)和 origin(起始基准时间)共同定义。若未指定起始基准时间,默认以 0001-01-01 00:00:00 为基准计算。
日期计算公式:
代表基准时间到达目标时间所需的周期数
语法
DAY_CEIL(<date_or_time_expr>)
DAY_CEIL(<date_or_time_expr>, <origin>)
DAY_CEIL(<date_or_time_expr>, <period>)
DAY_CEIL(<date_or_time_expr>, <period>, <origin>)
参数
| 参数 | 说明 |
|---|---|
<date_or_time_expr> | 参数是合法的日期表达式,支持输入 date/datetime/timestamptz 类型,具体格式请查看 timestamptz的转换, datetime 的转换 和 date 的转换 |
<period> | 参数是指定每个周期包含的天数,类型为 INT。若未指定,默认周期为 1 天。 |
<origin> | 参数是周期计算的起始基准时间,支持 date/datetime 类型 |
返回值
返回类型为 TIMESTAMPTZ, DATETIME 或 DATE。返回的是一个日期或时间值,表示将输入值向上舍入到指定天数周期的结果。
若输入有效,返回与 datetime 类型一致的取整结果:
- 若输入为 TIMESTAMPTZ 类型,则会先将其转换为 local_time(如:
2025-12-31 23:59:59+05:00在会话变量为+08:00的情况下代表的local_time为2026-01-01 02:59:59),再进行 DAY_CEIL 计算操作。 - 若输入的时间值(
<date_or_time_expr>和<period>)同时包含 TIMESTAMPTZ 和 DATETIME 类型,则输出 DATETIME 类型。
<date_or_time_expr> 与 <origin> 输入都 DATE 类型时,返回 DATE 类型, 否则返回 DATETIME 类型.
特殊情况:
- 任何参数为 NULL 时,返回 NULL;
- 若 period 为负数或 0,返回错误;
- 若取整结果超出日期类型支持的范围(如 '9999-12-31' 之后),报错。
- 带有 scale 的输入的datetime,返回值带有 scale,小数部分为 0.
- 若
<origin>日期时间在<period>之后,也会按照上述公式计算,不过周期 k 为负数。
举例
-- 以五天为一周期向上取整
select day_ceil( cast("2023-07-13 22:28:18" as datetime), 5);
+------------------------------------+
| day_ceil("2023-07-13 22:28:18", 5) |
+------------------------------------+
| 2023-07-15 00:00:00 |
+------------------------------------+
-- 带有 scale 输入的日期时间,返回值带有 scale 且全部小数为 0
select day_ceil( "2023-07-13 22:28:18.123", 5);
+-----------------------------------------+
| day_ceil( "2023-07-13 22:28:18.123", 5) |
+-----------------------------------------+
| 2023-07-15 00:00:00.000 |
+-----------------------------------------+
-- 不指定周期,默认一天向上取整
select day_ceil("2023-07-13 22:28:18");
+---------------------------------+
| day_ceil("2023-07-13 22:28:18") |
+---------------------------------+
| 2023-07-14 00:00:00 |
+---------------------------------+
-- 只有起始日期和指定日期
select day_ceil("2023-07-13 22:28:18", "2021-07-01 12:22:34");
+--------------------------------------------------------+
| day_ceil("2023-07-13 22:28:18", "2021-07-01 12:22:34") |
+--------------------------------------------------------+
| 2023-07-14 12:22:34 |
+--------------------------------------------------------+
-- 指定周期为 7 天(1 周),自定义基准时间为 2023-01-01 00:00:00
select day_ceil("2023-07-13 22:28:18", 7, "2023-01-01 00:00:00");
+-----------------------------------------------------------+
| day_ceil("2023-07-13 22:28:18", 7, "2023-01-01 00:00:00") |
+-----------------------------------------------------------+
| 2023-07-16 00:00:00 |
+-----------------------------------------------------------+
-- 日期时间刚好是周期的起点
select day_ceil("2023-07-16 00:00:00", 7, "2023-01-01 00:00:00");
+-----------------------------------------------------------+
| day_ceil("2023-07-13 22:28:18", 7, "2023-01-01 00:00:00") |
+-----------------------------------------------------------+
| 2023-07-16 00:00:00 |
+-----------------------------------------------------------+
-- 输入为 DATE 类型,周期为 3 天
select day_ceil(cast("2023-07-13" as date), 3);
+-----------------------------------------+
| day_ceil(cast("2023-07-13" as date), 3) |
+-----------------------------------------+
| 2023-07-14 |
+-----------------------------------------+
-- 周期时间为零,返回 NULL
select day_ceil(cast("2023-07-13" as date), 0);
+-----------------------------------------+
| day_ceil(cast("2023-07-13" as date), 0) |
+-----------------------------------------+
| NULL |
+-----------------------------------------+
--- 若 `<origin>` 日期时间在 `<period>` 之后,也会按照上述公式计算,不过周期 k 为负数。
select day_ceil('2023-07-13 19:30:00.123', 4, '2028-07-14 08:00:00');
+---------------------------------------------------------------+
| day_ceil('2023-07-13 19:30:00.123', 4, '2028-07-14 08:00:00') |
+---------------------------------------------------------------+
| 2023-07-17 08:00:00.000 |
+---------------------------------------------------------------+
-- TimeStampTz类型样例, SET time_zone = '+08:00'
-- 将变量值转换为 local_time(2026-01-01 02:59:59)后再做 DAY_CEIL 操作
SELECT DAY_CEIL('2025-12-31 23:59:59+05:00');
+---------------------------------------+
| DAY_CEIL('2025-12-31 23:59:59+05:00') |
+---------------------------------------+
| 2026-01-02 00:00:00+08:00 |
+---------------------------------------+
-- 若参数同时包含 TimeStampTz 和 Datetime 类型,则输出 DateTime 类型
SELECT DAY_CEIL('2025-12-31 23:59:59+05:00', '2025-12-15 00:00:00.123');
+------------------------------------------------------------------+
| DAY_CEIL('2025-12-31 23:59:59+05:00', '2025-12-15 00:00:00.123') |
+------------------------------------------------------------------+
| 2026-01-02 00:00:00.123 |
+------------------------------------------------------------------+
-- 周期为负数
mysql> select day_ceil("2023-07-13 22:28:18", -2);
ERROR 1105 (HY000): errCode = 2, detailMessage = (10.16.10.3)[E-218]Operation day_ceil of 2023-07-13 22:28:18, -2 out of range
-- 返回日期超过最大范围,返回错误
select day_ceil("9999-12-31", 5);
ERROR 1105 (HY000): errCode = 2, detailMessage = (10.16.10.3)[E-218]Operation day_ceil of 9999-12-31 00:00:00, 5 out of range
-- 任意参数为 NULL,返回 NULL
select day_ceil(NULL, 5, "2023-01-01");
+---------------------------------+
| day_ceil(NULL, 5, "2023-01-01") |
+---------------------------------+
| NULL |
+---------------------------------+