字符集&字符编码方式
字符集(Character set)是多个字符的集合,字符集种类较多,每个字符集包含的字符个数不同,这里的字符可以是英文字符,汉字字符,或者其他国家语言字符。
常见字符集包括:ASCII字符集、LATIN1字符集、GB2312字符集、GBK字符集、GB18030字符集、Unicode字符集等。字符编码方式是用一个或多个字节表示字符集中的一个字符。每种字符集都有自己特有的编码方式,因此同一个字符,在不同字符集的编码方式下,会产生不同的二进制。ASCII是基于罗马字母表的一套字符集,它采用1个字节的低7位表示字符,高位始终为0。LATIN1字符集相对于ASCII字符集做了扩展,仍然使用一个字节表示字符,但启用了高位,扩展了字符集的表示范围。GB2312、GBK、GB18030字符集是支持中文的字符集,字符集范围GB2312<GBK< GB18030。GBK字符集的字符有一字节编码和两字节编码方式。对于00-7F的字符与ASCII保持一致,汉字采用2个字节表示。第一字节范围是81-FE,避免与00-7F冲突。Unicode字符集是计算机科学领域里的一项业界标准,支持了所有国家的文字字符。Unicode字符集有好几种编码方式,比如常见的utf-8,utf-16,utf-32等。Utf8采用1-4个字节表示字符,utf-16采用固定的2个字节,utf-32则采用4个字节存储。
MySQL与字符集
只要涉及到文字的地方,就会存在字符集和编码方式。对于MySQL数据库系统而言,用户从MySQL client端敲入一条sql语句,通过TCP/IP传递给MySQL server进程,到最终存入server端的文件,每个环节都涉及到字符存储。涉及到字符存储的地方,就涉及到字符集编码,通过MySQL提供的系统变量就可见一斑。MySQL字符集设置系统变量以及含义如下表:
变量名
含义
character_set_server
默认的内部操作字符集
character_set_client
客户端来源数据使用的字符集
character_set_connection
连接层字符集
character_set_results
查询结果字符集
character_set_database
当前选中数据库的默认字符集
character_set_system
系统元数据(字段名等)字符集
以上这些参数如何起作用
1.库、表、列字符集的由来
(1).建库时,若未明确指定字符集,则采用character_set_server指定的字符集。
(2).建表时,若未明确指定字符集,则采用当前库所采用的字符集。
(3).新增,修改表字段时,若未明确指定字符集,则采用当前表所采用的字符集。
2.更新、查询涉及到得字符集变量
用户在更新(插入,删除,修改),查询数据库时,最常使用的字符集变量主要包含character_set_client,character_set_connection,character_set_result。
更新流程字符集转换过程:character_set_client-》character_set_connection-》表字符集。
查询流程字符集转换过程:表字符集-》character_set_result
PS:个人认为character_set_connection连接字符集设置有点冗余,因为最终都是要转换到表字符集的。
3.character_set_database
这个参数是当前默认数据库的字符集,比如执行use xxx后,当前数据库变为xxx,若xxx的字符集为utf8,那么这个变量值就变为utf8。因此这个参数是供系统设置,无需人工设置。
mysql字符编码转换流程
如果以上各个系统变量的设置不一致,比如character_set_client为UTF8,而character_set_database为GBK,则会出现需要进行编码转换的情况。那么字符集转换的原理是什么?假设GBK字符集的字符串“小明”,需要转为UTF8字符集存储,实际就是对于“小明”字符串中的每个汉字去UTF8编码表里面查询对应的二进制,然后存储,仅此而已,编码转换并不涉及到复杂的算法。mysql字符集转换主要涉及到几个步骤:
1) 将数据从character_set_client设置转换为character_set_connection设置;
2) 将character_set_connection设置转为表字段的字符集设置;
3) 将操作结果从表字段字符集转为character_set_results设置。