Javase-字符集

2. 字符集

2.1 基础知识

  • 字符(Character):各种文字和符号的总称,包括各国家文字、标点符号、图形符号、数字等。

  • 字符集(Character set):字符及其对应码点的集合(有些字符集也会包含字符编码规则),字符集种类多,且不同字符集一般包含的字符个数不同。计算机处理各种字符集文字,就需要进行字符编码,以便计算机能够识别和存储各种字符。

  • 码点:字符集中的每个字符都有一个对应的数字,即码点,码点相当于字符的ID,如ASCII中字符’A’的码点为65(计算机存储的不一定是码点直接对应的二进制,编码规则决定了码点映射为二进制的规则)。

  • 编码:把字符按照指定字符集编码成字节(把相应码点映射为具体的二进制),实现了从字符到计算机存储内容的映射,如ASCII中字符’A’在计算机中具体存储的是01000001。

  • 解码:把字节按照指定字符集解码成字符。

  • 乱码:乱码产生的原因一般有三方面:

    • 编码引起的乱码
    • 解码引起的乱码以及
    • 缺少某种字体库引起的乱码(需要安装相应的字体库)

    (多数乱码问题是由不合适的解码方式造成的。编码的时候用一种编码表,解码的时候用另一种不兼容的编码表,就会出现乱码。)

2.2 常见字符集

(1) ASCII

计算机发明之初,只考虑了128个字符并制定了标准,这个标准就是ASCII字符集。ASCII的码点是从0到127,共128个字符,用7个比特位就可以表示完。单字节编码。

  • 计算机的最小存储单位是一个字节(byte,8位),所以ASCII码中最高位置0,剩下的7位表示ASCII中的字符。
  • 0-31,127对应的字符是一些不可以打印的字符,这些字符一般用于控制目的,且多数不常用,32-126表示的字符都是可打印字符。
  • 随着发展,ASCII码已经不能满足很多国家的使用,于是多个国家都发明了自己字符集和编码方式,不过为了保持与ASCII码的兼容性,最高位为0时表示ASCII码,为1时表示自己国家的字符。
(2) GB2312

中文的第一个标准。GB2312主要收录简体中文和常见符号,共7445个图形字符(不包括繁体字)。固定使用两个字节表示汉字。多字节编码,每个字符可以由1个、2个字节组成。

  • 分区表示:GB2312中对汉字(仅仅是汉字)进行“分区”处理,每区含有94个汉字/符号,共计94个区。

    • 01-09区(682个):特殊符号、数字、英文字符、制表符等,包括拉丁字母、希腊字母、日文平假名及片假名字母、俄语西里尔字母等在内的682个全角字符;
    • 10-15区:空区,留待扩展;
    • 16-55区(3755个):常用汉字(也称一级汉字),按拼音排序;
    • 56-87区(3008个):非常用汉字(也称二级汉字),按部首/笔画排序;
    • 88-94区:空区,留待扩展。
  • 双字节表示:用所在的区(1-87区)和位(1-94位)来表示字符(的方法称为区位码。(在储存时,电脑会在区位码上加上特定数字(0xA0)后才保存进内存以确保和其他编码兼容(如 ASCII))。

    • 高位字节(两个字节中前面的字节为第一字节)存储”区码“(范围0xA1-0xF7(等于把01-87区的区号加上0xA0)),
    • 低位字节存储”位码“(范围0xA1-0xFE(等于把01-94加上0xA0))。
    • 第一个字节(区码)范围是161(0xA1,1010 0001) - 247(0xF7,1111 0111),
    • 第二个字节(位码)范围是161(0xA1,1010 0001) - 254(0xFE,1111 1110),86*93=7998。
  • 兼容ASCII:最高位是0,读取一个字节,认为是ASCII字符;最高位是1,则两个字节一起读取,并按照GB2312规则进行解析。

(3) GBK

是GB2312的拓展,兼容GB2312,即GB2312编码的字符的二进制表示,在GBK编码里是完全一样的。GBK增加了一万四千多个汉字,共计约21000汉字,包括繁体字。多字节编码,每个字符可以由1个、2个字节组成,汉字占两个字节。

  • 第一个字节范围是1000 0001(十进制129) - 1111 1110(十进制254),第二个字节范围是0100 0000(十进制64) - 0111 1110(十进制126)和1000 0000(十进制128) - 1111 1110(十进制254)。
(4) GB18030

向下兼容GBK,增加了五万五千多个字符,共七万六千多个字符。包括了很多少数民族字符,以及中日韩统一字符。变长多字节编码,每个字可以由1个、2个或4个字节组成,完全支持Unicode。

  • 变长编码:两个字节表示不了GB18030中的所有字符(65536<70000),所以GB18030使用变长编码,有的字符是两个字节,有的字符是四个字节。在两字节编码中,字节表示范围与GBK一样。
  • GB18030包含三种长度的编码:单字节的ASCII、双字节的GBK(略带扩展)、以及用于填补所有Unicode码位的四字节UTF区块。
(5) Big5

港澳台地区的大五码。Big5是针对繁体中文的,广泛用于台湾香港等地。Big5包括1万3千多个繁体字,固定使用两个字节表示。

(6) Unicode

统一码、万国码、单一码、标准万国码,是业界的一种标准。范围是 0x0000 - 0x10FFFF , 可以容纳一百多万个字符(没有规定编码规则,需要指定编码规则-UTF-8/UTF-16/UTF-32)。

  • UTF-32:定长编码,不兼容ASCII,有大端(Big Endian, BE,符合阅读习惯)和小端(Little Endian, LE,有利于数据处理)两种方式,字符统一使用 4 个字节(空间利用率低,UTF-32是因为UTF-16编码方式不能表示全部的字符而扩充的编码方式)

  • UTF-16:变长字符编码(2 字节 或者 4 字节),不兼容ASCII,基本平面的字符占用 2 个字节,辅助平面的字符占用 4 个字节。UTF-16也有UTF-16LE和UTF-16BE之分。

    • 基本平面/辅助平面:Unicode有很多字符,进行分区存放,每个区可存放 65536 个(2^16)字符,称为一个平面。目前,一共有 17 个(2^5)平面(65536*17 = 1,114,112‬ 也就是110多万)。Unicode最前面的 65536 个字符位,称为基本平面(BMP ),它的码点范围是从 0 到 2^16-1,16 进制从 U+0000 到 U+FFFF。所有最常见的字符都放在这个平面,这是 Unicode 最先定义和公布的一个平面。剩下的字符都放在辅助平面(SMP ),从 U+010000 到 U+10FFFF。
    • UTF-16常用于系统内部编码,windows系统默认的Unicode编码就是UTF-16。
  • UTF-8:变长字符编码(1字节,2字节,3字节 或者 4 字节),英文数字等只占一个字节(兼容ASCII),大多数汉字占3个字节(非常见字可能会超过3个字节)。

    对于单字节的符号,字节的第一位设为0,后面7位为这个符号的unicode码。因此对于英语字母,UTF-8编码和ASCII码是相同的。对于n字节的符号(n>1),第一个字节的前n位都设为1,第n+1位设为0,后面字节的前两位一律设为10。剩下的没有提及的二进制位,全部为这个符号的unicode码。(具体规则如下表)

    UTF-8编码方式(x表示可用编码的位,x的值要用Unicode字符对应的二进制值从右往左依次填充,剩下的x置0)Unicode字符不同码点值对应不同的编码(十六进制)
    0XXXXXXX(ASCII码)0-7F之间的字符用1个字节表示
    110XXXXX 10XXXXXX80-7FF之间的字符用2个字节表示
    1110XXXX 10XXXXXX 10XXXXXX800-FFFF之间的字符用3个字节表示
    11110XXX 10XXXXXX 10XXXXXX 10XXXXXX1 0000-10 FFFF之间的字符用4个字节表示

    (例,已知“严”的unicode是4E25(100111000100101),根据上表,可以发现4E25处在第三行的范围内(0000 0800-0000 FFFF),因此“严”的UTF-8编码需要三个字节,即格式是“1110xxxx 10xxxxxx 10xxxxxx”。然后,从“严”的最后一个二进制位开始,依次从后向前填入格式中的x,多出的位补0。这样就得到了,“严”的UTF-8编码是“11100100 10111000 10100101”,转换成十六进制就是E4B8A5。[实例转载于](UTF-8编码规则(转) - 奋斗者 - 博客园 (cnblogs.com)))

    (注:UTF-8兼容ASCII,在网络上数据传输英文字符只需要1个字节,可以节省带宽资源。所以大部分的网络应用都使用UTF-8编码。)

ASCII,GBxxxx,Big5等字符集都包含字符编码规则(方案)。Unicode仅是一个字符集,不含字符编码规则,需要指定编码方案UTF-8/16/32来实现字符编码。

锟斤拷

锟斤拷是一个常见的中文乱码,它一般在UTF-8和中文编码比如和GBK的转化过程中产生,Unicode中有一个特殊的替换符号� ,专门用于表示无法识别或展示的文字 ,然而有些编辑器会用UTF-8编码是,会把无法识别或展示的字符自动替换为这个替换符号,用于提示用户,在UTF-8编码后是一个三字节长度的二进制数字,对应的十六进制为EF BF BD,如果用户在编辑器替换后点了保存,这个特殊符号就会被写入文件内容进行保存,如果有两个� � 替换符号连在一起,内存中就会有十六进制的 EF BF BD EF BF BD,如果这个时候用GBK进行解码读取,就会出现锟(EF BF)斤(BD EF)拷(BF BD),所以锟斤拷是从UTF-8的两个连在一起的替换符号变来的。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值