1、问题描述:
在C++中封装的MySQL操作在插入中文时失败。返回失败信息如下:
Incorrect string value: '\xB2\xE5\xC8\xEB\xD6\xD0...' for column 'file_path' at row 1
2、问题分析:
刚开始时的时候我在VS中打印出要插入的中文字符是乱码,以为是编译器和数据库的编码格式的问题,在网上找了解决方案都是修改服务器的编码格式,或者修改MySQL Server 8.0 Data中my.ini中的编码格式,但是都没作用。最后一步步调试跟踪后发现:
(1)乱码问题:
乱码问题是我在将stringstream转换为string时使用了mysql.h中的:
unsigned long STDCALL mysql_real_escape_string(MYSQL *mysql, char *to,
const char *from,
unsigned long length);
导致的问题,实际上在转换时使用stringstream中的str()函数即可解决。
(2)插入中文失败问题:
向数据库插入中文字符失败是发生在最后调用mysql.h中的mysql_query()发生了错误。即实际上在插入中文的时候最后是使用了以下函数:
int STDCALL mysql_query(MYSQL *mysql, const char *q);
此函数功能:向与指定的连接标识符关联的服务器中的当前活动数据库发送一条查询。如果没有设置字符集则以默认字符集插入。因此需要在插入前增加一条修改插入数据时使用的编码格式,即增加:
mysql_query(MYSQL *mysql,, "SET NAMES 'gbk'");
3、问题解决:
(1)乱码问题:
在将stringstream转义时不使用mysql.h中的以下函数:
unsigned long STDCALL mysql_real_escape_string(MYSQL *mysql, char *to,
const char *from,
unsigned long length);
使用stringstream中的str()函数即可解决:
stringstream str_tmp = “中文字符”;
string str = str_tmp.str():
(2)插入中文失败问题:
在最后向数据库插入中文时使用到了mysql.h中的以下函数:
int STDCALL mysql_query(MYSQL *mysql, const char *q);
在此函数前再增加:
mysql_query(MYSQL *mysql, "SET NAMES 'gbk'");
即以gbk格式向数据库写入数据。
4、附:
查看数据库系统、服务器等的字符集:
show variables like'character%';
查看表的默认字符集:
SHOW CREATE TABLE t_record_real;
修改表默认字符集:
ALTER TABLE t_record_real DEFAULT CHARACTER SET utf8mb4;
注:
MySQL 的“utf8”实际上不是真正的 UTF-8。“utf8”只支持每个字符最多三个字节,而真正的 UTF-8 是每个字符最多四个字节。MySQL 刚开始一直没有修复这个 bug,他们在 2010 年发布了一个叫作“utf8mb4”的字符集才是真正的“UTF-8”。
来源:CSDN
作者:king_weng
链接:https://blog.csdn.net/King_weng/article/details/103464743