MySQL字符乱码

解决乱码的方法是,在执行SQL语句之前,将MySQL以下三个系统参数设置为与服务器字符集character-set-server相同的字符集。

character_set_client:客户端的字符集。

character_set_results:结果字符集。

character_set_connection:连接字符集。

设置这三个系统参数通过向MySQL发送语句:set names gb2312

 

 

现在我们应该清楚,乱码发生在数据库、客户端、查询结果以及数据库连接这其中一个或多

个环节

+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

首先分析乱码的情况

1.写入数据库时作为乱码写入

2.查询结果以乱码返回

究竟在发生乱码时是哪一种情况呢?

我们先在mysql 命令行下输入

show variables like '%char%';

查看mysql 字符集设置情况:

 

mysql> show variables like '%char%';

+--------------------------+----------------------------------------+

| Variable_name           | Value                                 |

+--------------------------+----------------------------------------+

| character_set_client    | gbk                                   |

| character_set_connection | gbk                                    |

| character_set_database  | gbk                                    |

| character_set_filesystem | binary                                 |

| character_set_results   | gbk                                   |

| character_set_server    | gbk                                   |

| character_set_system    | utf8                                  |

| character_sets_dir      | /usr/local/mysql/share/mysql/charsets/ |

+--------------------------+----------------------------------------+

 

在查询结果中可以看到mysql 数据库系统中客户端、数据库连接、数据库、文件系统、查询

结果、服务器、系统的字符集设置

在这里,文件系统字符集是固定的,系统、服务器的字符集在安装时确定,与乱码问题无关

乱码的问题与客户端、数据库连接、数据库、查询结果的字符集设置有关

*注:客户端是看访问mysql 数据库的方式,通过命令行访问,命令行窗口就是客户端,通

过JDBC 等连接访问,程序就是客户端

我们在向mysql写入中文数据时,在客户端、数据库连接、写入数据库时分别要进行编码转

在执行查询时,在返回结果、数据库连接、客户端分别进行编码转换

现在我们应该清楚,乱码发生在数据库、客户端、查询结果以及数据库连接这其中一个或多

个环节

接下来我们来解决这个问题

在登录数据库时,我们用mysql --default-character-set=字符集-u root -p 进行连接,这时我们

再用show variables like '%char%';命令查看字符集设置情况,可以发现客户端、数据库连接、

查询结果的字符集已经设置成登录时选择的字符集了

如果是已经登录了,可以使用set names 字符集;命令来实现上述效果,等同于下面的命令:

set character_set_client = 字符集

set character_set_connection = 字符集

set character_set_results = 字符集

 

如果碰到上述命令无效时也可采用一种最简单最彻底的方法

 

一、Windows

 

1、中止MySQL服务

2、在MySQL的安装目录下找到my.ini如果没有就把my-medium.ini复制为一个my.ini即可

3、打开my.ini以后[client][mysqld]下面均加上default-character-set=utf8保存并关闭

4、启动MySQL服务

 

要彻底解决编码问题,必须使

 

| character_set_client    | gbk                                   |

| character_set_connection | gbk                                    |

| character_set_database   |gbk                                    |

| character_set_results    |gbk                                    |

| character_set_server     |gbk                                    |

| character_set_system     |utf8    

 

这些编码相一致,都统一。

 

 

如果是通过JDBC 连接数据库,可以这样写URL:

URL=jdbc:mysql://localhost:3306/abs?useUnicode=true&characterEncoding=字符集

JSP 页面等终端也要设置相应的字符集

数据库的字符集可以修改mysql 的启动配置来指定字符集,也可以在create database 时加上

default character set 字符集来强制设置database 的字符集

通过这样的设置,整个数据写入读出流程中都统一了字符集,就不会出现乱码了

为什么从命令行直接写入中文不设置也不会出现乱码?

可以明确的是从命令行下,客户端、数据库连接、查询结果的字符集设置没有变化

输入的中文经过一系列转码又转回初始的字符集,我们查看到的当然不是乱码

但这并不代表中文在数据库里被正确作为中文字符存储

举例来说,现在有一个utf8 编码数据库,客户端连接使用GBK 编码,connection 使用默认

的ISO8859-1(也就是mysql 中的latin1),我们在客户端发送中文这个字符串,客户端

将发送一串GBK 格式的二进制码给connection 层,connection 层以ISO8859-1 格式将这段

二进制码发送给数据库,数据库将这段编码以utf8 格式存储下来,我们将这个字段以utf8

格式读取出来,肯定是得到乱码,也就是说中文数据在写入数据库时是以乱码形式存储的,

在同一个客户端进行查询操作时,做了一套和写入时相反的操作,错误的utf8 格式二进制

码又被转换成正确的GBK 码并正确显示出来。



数据库字符乱码问题:

 

设置当前表的字符集:

1.sql>set nameslatinl;

再插入数据就不会有乱码

 

2.直接在sql命令行里设置

sql>set nameslatinl;

3.在操作系统文件里创建一个文件,里面写入setnames latinl;

mysql>system cattest.sql

set names latinl;

insert into studentvalues(1,'阮胜昌')

 

mysql>sourcetest.sql

 

mysql> system ls -al   //执行操作系统里面的命令

total 1656

drwxr-x--- 21 rootroot    4096 Jun 14 20:51 .

drwxr-xr-x 27 rootroot    4096 Jun 14 20:14 ..

-rw-r--r--  1 root root       0 Apr 1  2014 1

 

 

4.导入SQL时,加入默认字符集:

mysql -uroot -p123456--default-character-set=latinl oldboy < test.sql

 

5.

cat /etc/my.cnf

[client]

default-character-set=latinl.

 

[mysqld]

default-character-set=latinl#适合5.1及以前版本

character-set-server=latinl#适合5.5

 

 

保证不乱码的思想:

Linux系统,客户端,服务端,库,表,程序在换成统一的字符集

Linux系统字符集

[root@node201 ~]# cat/etc/sysconfig/i18n

LANG="en_US.UTF-8"

SYSFONT="latarcyrheb-sun16"

#LANG="zh_CN.GB2312"

#LANG="en"

#LANG="zh_CN.utf8"

 

客户端:

set names=latin1   1:是数字1

更改my.cnf客户端模块的参数,可以实现set names latin1的效果,并且永久生效

 

服务端:

[mysqld]

default-character-set=latinl#适合5.1及以前版本

character-set-server=latinl#适合5.5

 

mysql>createdatabase oldboy_utf8 default character set utf8 collate utf8_general_ci

 

 

总结

在执行DQL,DML 语句之前set names系统或库表的字符集

 


 

分割线
感谢打赏
江西数库信息技术有限公司
YWSOS.COM 平台代运维解决方案
 评论
 发表评论
姓   名:

Powered by AKCMS