DATE_FORMAT()只接受DATE/DATETIME/TIMESTAMP类型,字符串需先用STR_TO_DATE()转换;注意NULL处理、时区偏移、格式符大小写敏感(如%y≠%Y)、中文需手动映射,WHERE中使用会导致索引失效。

MySQL 的 DATE_FORMAT() 函数怎么写才不报错
直接用 DATE_FORMAT() 时最常遇到 FUNCTION DATE_FORMAT does not exist,不是函数不存在,而是你传了错误类型的值——它只接受 DATE、DATETIME 或 TIMESTAMP 类型,不能直接格式化字符串。比如 '2024-05-10' 看似像日期,但若字段是 VARCHAR,就得先转类型。
- 正确姿势:
DATE_FORMAT(STR_TO_DATE('2024-05-10', '%Y-%m-%d'), '%Y年%m月%d日') - 常见翻车点:对
NULL值调用会返回NULL,不报错但结果意外;需要提前用IFNULL()或COALESCE()处理 - 注意时区:函数输出不带时区信息,如果字段存的是 UTC 时间但你按本地格式化,结果会偏移——得先用
CONVERT_TZ()调整
常用格式化符号和坑点(%Y %m %d 到底对应什么)
DATE_FORMAT() 的格式符大小写敏感,且部分符号行为反直觉。比如 %y 是两位年份(24),%Y 是四位(2024);%m 是补零月份(05),%c 是无补零(5),但 %c 在某些旧 MySQL 版本里不支持。
- 星期相关:用
%W得到 'Monday',%w是数字(1=Monday),但注意 MySQL 默认周一是 1,而WEEK()函数默认周日为 0 —— 混用容易对不上 - 中文输出:MySQL 本身不生成中文月份或星期,
'%Y年%m月%d日'中的“年”“月”“日”是字面量,不是格式符;想输出“五月”得用CASE WHEN MONTH(date_col) = 5 THEN '五月'手动映射 - 24 小时制:
%H是 00–23,%h是 01–12,别把%h:%i %p(如 '02:30 PM')错写成%H:%i
在 SELECT 和 WHERE 中用 DATE_FORMAT() 的性能影响
在 WHERE 子句里对日期字段用 DATE_FORMAT() 会导致索引失效——因为函数作用于列,MySQL 无法走 B+ 树索引。例如 WHERE DATE_FORMAT(create_time, '%Y-%m') = '2024-05' 会全表扫描。
- 替代方案:用范围查询代替格式化,
WHERE create_time >= '2024-05-01' AND create_time - 如果必须格式化后过滤(比如查“周一的数据”),优先考虑生成计算列 + 索引:
ALTER TABLE t ADD COLUMN week_day TINYINT AS (WEEKDAY(create_time)) STORED,再给该列建索引 - 在
SELECT中格式化一般无性能问题,但若字段本身是TIMESTAMP且含微秒,DATE_FORMAT()会自动截断,不保留小数秒
和 STR_TO_DATE() 配合做解析时的典型错误
DATE_FORMAT() 是“出”,STR_TO_DATE() 是“进”,两者常一起用,但格式符必须严格一致。比如用 STR_TO_DATE('10/05/2024', '%d/%m/%Y') 解析,反过来用 DATE_FORMAT(..., '%m/%d/%Y') 就会把 10 月 5 日变成 '05/10/2024',顺序全乱。
- 验证方法:先用
STR_TO_DATE()解析,再用DATE()提取日期部分,确认是否符合预期 - 安全写法:统一用标准格式中转,比如先转成
DATE类型,再用DATE_FORMAT()输出目标格式,避免中间字符串歧义 - 注意分隔符:斜杠 /、短横 -、点 . 都要原样写进格式串,
'%Y-%m-%d'不能写成'%Y/%m/%d'去解析 '2024-05-10'


















