在MySQL开发中,DATE_FORMAT函数是处理时间格式化的常用工具,但不少开发者在使用时会遇到和字符集相关的奇怪问题,比如格式化后的中文内容出现乱码、特殊字符显示异常等。下面我们通过实际案例来梳理这些常见问题。

DATE_FORMAT函数字符集相关常见问题
1. 中文格式化标识符返回乱码
当使用DATE_FORMAT函数输出中文的月份、星期时,如果字符集配置不匹配,很容易出现乱码。比如我们想获取当前日期的中文月份:
-- 查看当前连接字符集 SHOW VARIABLES LIKE 'character_set_connection'; -- 格式化当前日期为中文月份 SELECT DATE_FORMAT(NOW(), '%Y年%m月') AS formatted_date;
如果character_set_connection不是utf8或者utf8mb4,返回的结果中中文部分可能会显示为问号或者乱码。
2. 特殊格式化字符显示异常
DATE_FORMAT函数支持很多格式化标识符,部分标识符返回的内容依赖字符集,比如%W返回星期全名,%M返回月份全名,如果字符集不匹配,这些英文或者本地化的内容也会出现显示问题。
3. 不同客户端返回结果不一致
有时候在命令行客户端查询DATE_FORMAT的结果正常,在应用程序中查询却出现乱码,这通常是应用程序的连接字符集没有和MySQL服务端匹配导致的。
问题产生原因
DATE_FORMAT函数返回的内容的字符集,默认和当前连接的character_set_connection一致。如果格式化后包含非ASCII字符(比如中文、特殊本地化字符),而客户端或者返回结果的字符集不支持这些字符,就会出现乱码或者显示异常。
另外,MySQL的lc_time_names系统变量决定了日期时间相关本地化字符串的语言,比如设置为zh_CN时,月份和星期会返回中文,如果这个变量没有正确设置,即使字符集正确,也可能返回英文内容而不是预期的中文。
解决方法
1. 统一字符集配置
首先确保MySQL服务端的字符集、客户端连接字符集、返回结果的字符集保持一致,推荐使用utf8mb4字符集,支持所有Unicode字符。可以在连接MySQL后执行以下语句设置连接字符集:
-- 设置连接字符集为utf8mb4 SET NAMES utf8mb4; -- 设置时间本地化语言为中文 SET lc_time_names = 'zh_CN';
2. 检查应用程序连接配置
如果是应用程序中调用DATE_FORMAT出现问题,需要在数据库连接配置中指定字符集,比如JDBC连接可以在URL中添加useUnicode=true&characterEncoding=utf8mb4参数,PHP连接时可以指定字符集为utf8mb4。
3. 验证格式化结果
可以通过简单的查询验证配置是否生效:
-- 验证中文月份格式化是否正常
SELECT DATE_FORMAT('2024-05-20', '%Y年%m月%d日 %W') AS test_date;如果返回的结果是2024年05月20日 星期一,说明字符集和本地化配置都正确。
注意事项
- 不要随意修改MySQL服务端的全局字符集配置,避免影响其他业务,优先在连接层面设置字符集。
lc_time_names变量的作用范围是会话级别,设置后只对当前连接生效,应用程序中如果需要中文格式化,每次连接都需要设置,或者配置连接初始化语句。- 如果使用的是老版本的MySQL,需要注意utf8字符集只支持3字节的Unicode字符,如果有4字节的字符(比如部分emoji),需要使用utf8mb4字符集。
MySQLDATE_FORMAT字符集时间格式化乱码修改时间:2026-06-01 21:06:56