SET NAMES utf8mb4 仅设置当前连接字符集,无法修复源文件编码错误或配置未生效等问题;必须确保SQL文件为UTF-8无BOM编码、my.cnf正确配置并重启服务、客户端连接三件套(client/connection/results)全为utf8mb4,且乱码数据需按原始错误路径反向转换。

为什么 SET NAMES utf8mb4 之后还是乱码?
因为 SET NAMES utf8mb4 只管当前连接层,不解决源头问题。如果导入的 SQL 文件本身不是 UTF-8 编码(比如用 Windows 记事本另存为 ANSI 导出的),那再怎么设连接字符集也没用——MySQL 拿到的就是错字节流。
- 先用 VS Code 或 Notepad++ 打开你的
.sql文件,右下角看编码,如果不是UTF-8 without BOM,就「另存为」选这个编码 - Linux/macOS 下可用
file -i your_file.sql查实际编码;Windows 命令行用chcp看当前代码页,65001 才是 UTF-8 -
mysqldump导出时必须加--default-character-set=utf8mb4,否则默认用latin1
my.cnf 配置写对了,为什么重启后 SHOW VARIABLES 还是 latin1?
常见原因是配置没生效或被覆盖。MySQL 启动时会读多个配置文件(/etc/my.cnf、/etc/mysql/my.cnf、~/.my.cnf),优先级高的会覆盖低的。
- 确认你改的是 MySQL 实际加载的配置文件:运行
mysql --help | grep "Default options"查路径 -
[mysqld]段必须加skip-character-set-client-handshake = ON,否则客户端硬发latin1,服务端照收 -
[client]和[mysql]段都要写default-character-set = utf8mb4,不然命令行工具自己用错编码 - Linux 用
sudo systemctl restart mysql,Windows 必须通过「服务管理器」重启,直接 kill 进程不重载配置
用 Navicat / DBeaver 导入 SQL,中文显示正常但查出来是乱码?
图形工具会自动声明字符集,掩盖真实连接状态。它可能把 character_set_client 设成 utf8mb4,但 character_set_connection 或 character_set_results 仍是 latin1,导致 INSERT 正常、SELECT 返回乱码。
- 别信图形界面的「字符集设置」,登录命令行执行
SHOW VARIABLES LIKE 'character%';,只盯这三项:character_set_client、character_set_connection、character_set_results - 三者必须全是
utf8mb4,缺一不可;任一为latin1或gbk,SELECT 就会解错 - Navicat 的「高级」选项里勾选「使用 MySQL 字符集」,DBeaver 要在连接属性里手动填
characterEncoding=utf8mb4
数据已经乱码了,还能救回来吗?
能,但不能只改表结构。乱码本质是“用 A 编码存、用 B 编码读”,修复得按原错路径反向还原——比如原本用 latin1 存的中文,现在要以 latin1 读出来,再转成 utf8mb4 存回去。
- 先确认当前乱码形态:如果显示
我,大概率是 UTF-8 字节被当latin1解;如果显示涓?鎴?,可能是 GBK 被当latin1 - 用
SELECT HEX(col_name) FROM table_name LIMIT 1;看原始字节,再对照编码表判断原始编码 - 修复语句类似:
UPDATE table_name SET col_name = CONVERT(CAST(CONVERT(col_name USING latin1) AS BINARY) USING utf8mb4);(具体转换链取决于原始错误) - 操作前务必备份,这种转换不可逆,且对大表性能影响明显
SHOW VARIABLES LIKE 'character%' 把连接三件套钉死,再回头查文件编码和配置加载路径。


















