Java与数据库交互中文乱码的根本原因是写入和读取编码不一致,主要发生在JDBC连接层、数据库服务端配置及表字段字符集三者未对齐;须确保MySQL服务器、数据库、表字段均设为utf8mb4,并在JDBC URL中显式指定useUnicode=true&characterEncoding=utf8mb4,且必须使用PreparedStatement传参。

Java 与数据库交互时出现中文乱码,根本原因在于“写入时用的编码”和“读取时用的编码”不一致,而这个不一致往往发生在 JDBC 连接层、数据库服务端配置、表字段字符集三者之间。只要其中一环没对齐,比如 Java 程序以 UTF-8 发送数据,但数据库连接被默认当成 ISO-8859-1 解析,或者表本身是 latin1 编码,结果就是存进去就变问号或乱码,读出来也一样。
确保数据库服务端字符集正确
MySQL 是最常出问题的场景。需确认以下三项均为 UTF-8 兼容编码(推荐 utf8mb4):
- 服务器默认字符集:
character_set_server = utf8mb4 - 数据库创建时指定:
CREATE DATABASE mydb CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci; - 数据表及字段也显式声明:
CHARACTER SET utf8mb4
JDBC 连接字符串必须显式声明编码
不能依赖默认值。URL 中要强制带上编码参数,例如 MySQL:
jdbc:mysql://localhost:3306/mydb?useUnicode=true&characterEncoding=utf8mb4&serverTimezone=Asia/Shanghai
立即学习“Java免费学习笔记(深入)”;
在 Java 中初始化和管理阿里云 SDK客户端。包括单例模式、线程安全、endpoint 与 region 配置、VPC 终端节点、同步与异步等。
-
useUnicode=true启用 Unicode 支持 -
characterEncoding=utf8mb4指定客户端与服务端通信使用的字符集 -
serverTimezone虽非编码相关,但缺失可能引发隐式异常,间接干扰连接初始化
避免 PreparedStatement 之外的字符串拼接
用 String sql = "INSERT INTO t VALUES ('" + name + "')" 这种方式拼 SQL,会绕过 JDBC 的编码处理机制,导致 JVM 字符串转字节时按平台默认编码(如 Windows 的 GBK)执行,再被数据库按 utf8mb4 解析,必然乱码。务必使用:
-
PreparedStatement占位符传参 - 所有文本内容都走
setString()方法,由 JDBC 驱动自动完成编码转换
验证连接实际生效的字符集
运行时可通过 SQL 查询确认当前连接的编码是否符合预期:
SELECT @@character_set_client, @@character_set_connection, @@character_set_results;
三者应均为 utf8mb4。若不是,说明连接参数未生效,需检查 URL 是否被中间件(如 Druid、HikariCP)覆盖,或是否存在多数据源配置冲突。

















