经常有朋友问到 mysql 的乱码问题。得到的答案多半是说:要保证编码一致,甚至php程序文件也要做到编码一致。其实不然!背景:
我还是在 mysql4 时代使用过 mysql,他没有编码问题,但也没有存储过程。所以就改用 sql server 了。最近因项目需求,又把 mysql 捡起来了。也测试了一下 mysql 的语言编码问题
我安装的是 mysql 5.1.47 版本,安装时选则了 utf8 作为默认语言
但我仍然喜欢使用 gbk 编码,因为编辑 utf-8 编码的文件需要用编程工具,而我只喜欢用 记事本于是我在上述环境中以 DEFAULT CHARSET=gbk 建库建表
并在 mysql_query('set names gbk'); 之后进行数据库操作。一直如此,并无任何问题。后来有一个必须为 utf-8 编码的页面,他还要使用那个 gbk 编码的库中的数据。怎么办呢?直接的想法就是取出数据后再用 iconv 函数转码。很是费劲吧?其实 mysql 已经做的很好了,只需要设置一下语言
mysql_query('set names utf8');
于是查询结果都是 utf-8 编码的了
不错!
于是我向 gbk 编码的表中插入 utf-8 编码的数据,然后用 gbk 编码读回(set names gbk)
真不错!
刚才插入的数据已然以 gbk 编码展示,一点乱码也没有
请有兴趣的朋友发表高论!
谢绝顶贴!
我还是在 mysql4 时代使用过 mysql,他没有编码问题,但也没有存储过程。所以就改用 sql server 了。最近因项目需求,又把 mysql 捡起来了。也测试了一下 mysql 的语言编码问题
我安装的是 mysql 5.1.47 版本,安装时选则了 utf8 作为默认语言
但我仍然喜欢使用 gbk 编码,因为编辑 utf-8 编码的文件需要用编程工具,而我只喜欢用 记事本于是我在上述环境中以 DEFAULT CHARSET=gbk 建库建表
并在 mysql_query('set names gbk'); 之后进行数据库操作。一直如此,并无任何问题。后来有一个必须为 utf-8 编码的页面,他还要使用那个 gbk 编码的库中的数据。怎么办呢?直接的想法就是取出数据后再用 iconv 函数转码。很是费劲吧?其实 mysql 已经做的很好了,只需要设置一下语言
mysql_query('set names utf8');
于是查询结果都是 utf-8 编码的了
不错!
于是我向 gbk 编码的表中插入 utf-8 编码的数据,然后用 gbk 编码读回(set names gbk)
真不错!
刚才插入的数据已然以 gbk 编码展示,一点乱码也没有
请有兴趣的朋友发表高论!
谢绝顶贴!
我理解,这是通知 mysql 下面的操作我将以 gbk 编码进行。与 mysql 表的实际编码无关,编码转换由 mysql 自行完成
向 gbk 编码的表中插入 utf-8 编码的数据,然后用 gbk 编码读回(set names gbk)
这样子是可以,但是难道每次进行查询的时候都要set names??
而且,对于一个网站页面编码不一致,甚至错综复杂的网站来说,比如新闻页,你在这个页面插入utf8的,另一个页面又是gbk的,那你在某个列表显示或详细内容显示的时候(通过参数id动态展示),那你查询之前是set names gbk还是set names utf8???
而且你set names什么编码,你的页面的编码页得什么编码。
之所以说要将php或html文件的存储编码也设为一样,是因为如果文件编码不一样,而文件里又直接写入了中文,那这部分中文也会乱码(虽然从数据库里读出的数据不会)
呵呵 我还是沉默 当个旁观者吧
mysql_select_db('test');
mysql_query("set names 'gbk'");
//mysql_query("set names 'utf8'");
mysql_query("insert into house set `name`='gbk名字', `addr`='gbk地址', `dev`='gbk其他测试'");
echo 'ok';查询mysql_connect('localhost', 'root','root');
mysql_select_db('test');
//mysql_query("set names 'gbk'");
mysql_query("set names 'utf8'");
$query=mysql_query("SELECT * FROM `house` WHERE 1");
$data=array();
while($rt = mysql_fetch_array($query)){
$data[]=$rt;
}
print_r($data);我的测试,文件的存储编码是utf-8
mysql_query("set names 'gbk'");和mysql_query("set names 'utf8'");后插入的数据,不管之前set names什么编码,另一部分的编码始终都是乱码的。
估计您是在用WIN98吧?
没有引号,我不知道你的mysql是什么版本,我的如加上引号就错了
所以我只远程在服务器上工作XP 的虽能编辑 utf-8 编码文件,但新建的文件保存为 utf-8 时就有 BOM 头了。估计你很喜欢
===================================这个至少不是全部,我最近一直用xp系统【就2台】,没这种情况
我的是mysql-essential-5.1.45-win32,我一直都加了引号的,没有错啊。
难道是版本不一样的原因??
此时数据的流程大致是utf8->utf8->gbk(数据->处理编码->入库)
2 取出数据的时候如果指定set names utf8的话,是没有问题的。gbk->utf8->页面
但是你指定set names gbk的话,大致是gbk->gbk->页面 肯定是有乱码的如果在上述1中,插入并指定set names gbk的话 同时取出时set names gbk 是没问题的。插入取出的页面需皆为utf8编码。记事本完全可以编辑 utf-8,前提条件是不要把记事本的概念局限在windows提供记事本上 世界上有其他非常好用的记事本
===================================
"SET NAMES ''"//语言,加不加''都可 版本 5.1.30
说的有误导 取出数据的页面是utf8的 有乱码 是gbk的话 没有乱码 恩 得出的结果与你的一样
/***************************/
对于一个编码为gbk的表:
1 插入数据的时候:你的数据编码为a 那么插入之前set names a
2 读出数据的时候:你的页面编码为b 那么select之前set names b
做到以上两点 就可以实现无乱码 就算你插入的数据编码为a 读出的时候编码设为b 也依然可保证无乱码出现
/***************************/
不知道这样理解有没有偏差 另外 上述测试在两种编码之间进行的 比如表为默认的latin1 插入utf8 读出gbk是不是也适合上述规律 还需测试一下
$hex = "";
$i = 0;
do {
$hex .= sprintf("%02x", ord($str{$i}));
$i++;
}
while ($i < strlen($str));
return $hex;
}
对于这个有何高论?!
那程序默认了utf-8,当调用你的数据时发现是gbk怎么办? 那么,默认情况下该程序就可能不正常显示你的数据了,
好比,你做好的作品给用户,而这些用户通常是白痴(对于计算机来说),
他们不懂设置这个那个,甚至也是根本看不明白后台管理的术语。下面举两个例子:再假设,我写程序时,都标了英文注解(utf-8),
当我有天心血来潮时突然要发布到sourceforge或code.google,
如果当时我用中文注解(gbk),那岂不是又要重新一次?其实,平时我们尽都可以说家乡话(gbk),但为什么还要说普通话(utf-8)来交流,
但习惯了家乡话的人上网时会说一些别人看不明的术语。人类有人类的语言,机械有机械的语言,我们选择统一的语言是为了更好的交流,
但这个统一需要平时的习惯来作支撑。
------ 卑人浅见,多谢指教
关键你用这种编码存储时,当调用那一方也要支持,但调用的程序目前可能是自己,但当别人来调用时,
别人也是否支持这种编码格式的数据呢?
我想这个原理大概和Web Service一样,如果不用统一的协议,很难说是什么结论。
也正是这个原因,所以你用你的 utf-8 程序访问我的 gbk 数据库时只要声明一下 set names utf8 ,于是我的数据库就以 utf-8 编码向你提供数据;而我的 gbk 程序要从你的 utf8 数据库得到数据,也只需通知你的数据库 set names gbk 我需要 gbk 编码的数据如果仅仅是为了所谓的“统一”,那么为什么不统一到 gbk 下呢?你如何知道中国标准不会成为世界标准呢
---------------------------------------------
set character_set_client utf8; #通知mysql,客户端发送的是utf-8编码数据
set character_set_connection utf8 ;#客户端编码与存储引擎连接校对
set character_set_results utf8 ; #从存储引擎得到的数据转成utf8返回给客户端mysql帮我们完成了转换过程,不管是客户端gbk访问utf-8数据库,还是utf-8客户端访问gbk数据库,都没问题。
统一编码是为了系统的多语言性,移植性。
gbk的页面读其它语言的数据就肯定错了。
gbk要成为世界标准,最起码先得支持世界各国文字,编码区得扩充到和unicode一样。
存入时:character_set_client =〉
character_set_connection =〉
character_set_database(table/column )取出时:character_set_database(table/column ) =〉
character_set_connection =〉
character_set_results这个转换中,字符集必须相容(能一一对应当然最好),如果有latin1这样字符数很少的字符集,转换后必然会有字符丢失。我以前回复的帖子里有解释得更详细的,可以搜索到。
mysql里只有utf8,没有utf-8的编码名字
$con=@mysql_connect("localhost","root","123") or die("数据库无法连接");
$db=@mysql_select_db("my") or die("库无法连接");
header("Content-Type:text/html;charset=utf-8");
执行updata 语句的时候是
$con=@mysql_connect("localhost","root","123") or die("数据库无法连接");
$db=@mysql_select_db("my") or die("库无法连接");
mysql_query("set names GB2312");
这样不会有乱码 可是要是同一个网页同时执行这两个操作就乱了。怎么办?都说要统一编码 可是怎么把所有的编码都设置统一啊
header("Content-type:text/html;Charset=UTF-8;");
$link=mysql_connect("localhost","root","123456") or die("无法连接服务!");
mysql_select_db("codegbk",$link) or die("数据库无法选择");
mysql_query("set names utf8");
$rs = mysql_query("select *from user",$link);
$sql = "insert into user values(default,'测试乱码')";
mysql_query($sql);
while($row = mysql_fetch_array($rs)){
echo $row["username"]."<br/>";
}
?>
经过几次乱码的测试,只要在插入数据时候 set names 这个编码与页面的编码统一,而与数据库的编码无关系。在读数据的时候set names 这个编码与页面编码统一,也就相当与 set names 是告诉mysql 我要读取和存储什么样的编码数据。现在页面一直未出现问题.