第二篇:JAVA字符编码系列二:Unicode,ISO-8859-1,GBK,UTF-8编码及相互转换
 
1、函数介绍
在Java中,字符串用统一的Unicode编码,每个字符占用两个字节,与编码有关的两个主要函数为:
1)将字符串用指定的编码集合解析成字节数组,完成Unicode-〉charsetName转换
public byte[] getBytes(String charsetName) throws UnsupportedEncodingException 
 
2)将字节数组以指定的编码集合构造成字符串,完成charsetName-〉Unicode转换
public String(byte[] bytes, String charsetName) throws UnsupportedEncodingException
 
2、Unicode与各编码之间的直接转换
下面以对中文字符串"a中文"的编码转换为例,来了解各种编码之间的转换
1)Unicode和GBK
测试结果如下,每个汉字转换为两个字节,且是可逆的,即通过字节可以转换回字符串
String-GBK〉ByteArray:/u0061/u4E2D/u6587(a中文)-〉0x61 0xD6 0xD0 0xCE 0xC4
ByteArray-GBK〉String:0x61 0xD6 0xD0 0xCE 0xC4-〉/u0061/u4E2D/u6587(a中文)
 
2)Unicode和UTF-8
测试结果如下,每个汉字转换为三个字节,且是可逆的,即通过字节可以转换回字符串
String-UTF-8〉ByteArray:/u0061/u4E2D/u6587(a中文)-〉0x61 0xE4 0xB8 0xAD 0xE6%0x96 0x87
ByteArray-UTF-8〉String:0x61 0xE4 0xB8 0xAD 0xE6%0x96 0x87-〉/u0061/u4E2D/u6587(a中文)
3)Unicode和ISO-8859-1
测试结果如下,当存在汉字时转换失败,非可逆,即通过字节不能再转换回字符串
String-ISO-8859-1〉ByteArray:/u0061/u4E2D/u6587(a中文)-〉0x61 0x3F 0x3F
ByteArray-ISO-8859-1〉String:0x61 0x3F 0x3F-〉/u0061/u003F/u003F(a??)
 
3、Unicode与各编码之间的交叉转换
在上面直接转换中,由字符串(Unicode)生成的字节数组,在构造回字符串时,使用的是正确的编码集合,如果使用的不是正确的编码集合会怎样呢?会正确构造吗?如果不能正确构造能有办法恢复吗?会信息丢失吗?
 
下面我们就来看看这种情况,这部分可以说明在某些情况下虽然我们最终正确显示了结果,但其间仍然进行了不正确的转换。
 
1)能够正确显示的中间不正确转换
我们知道String-GBK〉ByteArray-GBK〉String是正确的,但如果我们采用String-GBK〉ByteArray-ISO-8859-1〉String呢?通过测试结果如下:
String-GBK〉ByteArray-ISO-8859-1〉String:/u0061/u4E2D/u6587(a中文)-〉0x61 0xD6 0xD0 0xCE 0xC4-〉/u0061/u00D6/u00D0/u00CE/u00C4(a????)
 
这时我们得到的字符串为?乱码“a????”,但是通过继续转换我们仍然可以复原回正确的字符串“a中文”,过程如下:
String-GBK〉ByteArray-ISO-8859-1〉String-ISO-8859-1〉ByteArray-GBK〉String
对应:/u0061/u4E2D/u6587(a中文)-〉0x61 0xD6 0xD0 0xCE 0xC4-〉/u0061/u00D6/u00D0/u00CE/u00C4(a????)-〉0x61 0xD6 0xD0 0xCE 0xC4-〉/u0061/u4E2D/u6587(a中文)
 
也就是我们在首次构造字符串时,我们用了错误的编码集合得到了错误的乱码,但是我们通过错上加错,再用错误的编码集合获取字节数组,然后再用正确的编码集合构造,就又恢复了正确的字符串。这时就属于是“能够正确显示的中间不正确转换”。在Jsp页面提交数据处理时常常发生这种情况。
 
此外能够正确显示的中间不正确转换还有:
String-UTF-8〉ByteArray-ISO-8859-1〉String-ISO-8859-1〉ByteArray-UTF-8〉String
String-UTF-8〉ByteArray-GBK〉String-GBK〉ByteArray-UTF-8〉String
对应:/u0061/u4E2D/u6587(a中文)-〉0x61 0xE4 0xB8 0xAD 0xE6%0x96 0x87-〉/u0061/u6D93/uE15F/u6783(a涓枃)-〉0x61 0xE4 0xB8 0xAD 0xE6%0x96 0x87-〉/u0061/u4E2D/u6587(a中文)
 
4、编码过程中错误诊断参考
1)一个汉字对应一个问号
在通过ISO-8859-1从字符串获取字节数组时,由于一个Unicode转换成一个byte,当遇到不认识的Unicode时,转换为0x3F,这样无论用哪种编码构造时都会产生一个?乱码。
2)一个汉字对应两个问号
在通过GBK从字符串获取字节数组时,由于一个Unicode转换成两个byte,如果此时用ISO-8859-1或用UTF-8构造字符串就会出现两个问号。
若是通过ISO-8859-1构造可以再通过上面所说的错上加错恢复(即再通过从ISO-8859-1解析,用GBK构造);
若是通过UTF-8构造则会产生Unicode字符"/uFFFD",不能恢复,若再通过String-UTF-8〉ByteArray-GBK〉String,则会出现杂码,如a锟斤拷锟斤拷
3)一个汉字对应三个问号
在通过UTF-8从字符串获取字节数组时,由于一个Unicode转换成三个byte,如果此时用ISO-8859-1构造字符串就会出现三个问号;用GBK构造字符串就会出现杂码,如a涓枃。

JAVA字符编码二:Unicode,ISO-8859,GBK,UTF-8编码及相互转换的更多相关文章

  1. 从Java String实例来理解ANSI、Unicode、BMP、UTF等编码概念

    转(http://www.codeceo.com/article/java-string-ansi-unicode-bmp-utf.html#0-tsina-1-10971-397232819ff9a ...

  2. Java 字符转码之UTF-8转为GBK/GB2312

    java跟python类似的做法,在java中字符串的编码是java修改过的一种Unicode编码,所以看到java中的字符串,心理要默念这个东西是java修改过的一种Unicode编码的编码. pa ...

  3. 【JAVA编码专题】JAVA字符编码系列一:Unicode,GBK,GB2312,UTF-8概念基础

    这两天抽时间又总结/整理了一下各种编码的实际编码方式,和在Java应用中的使用情况,在这里记录下来以便日后参考. 为了构成一个完整的对文字编码的认识和深入把握,以便处理在Java开发过程中遇到的各种问 ...

  4. JAVA字符编码一:Unicode,GBK,GB2312,UTF-8概念基础

    第一篇:JAVA字符编码系列一:Unicode,GBK,GB2312,UTF-8概念基础 来源:holen'blog   对字符编码与Unicode,ISO 10646,UCS,UTF8,UTF16, ...

  5. 【JAVA编码】 JAVA字符编码系列二:Unicode,ISO-8859,GBK,UTF-8编码及相互转换

    http://blog.csdn.net/qinysong/article/details/1179489 这两天抽时间又总结/整理了一下各种编码的实际编码方式,和在Java应用中的使用情况,在这里记 ...

  6. 关于JAVA字符编码:Unicode,ISO-8859-1,GBK,UTF-8编码及相互转换

    我们最初学习计算机的时候,都学过ASCII编码. 但是为了表示各种各样的语言,在计算机技术的发展过程中,逐渐出现了很多不同标准的编码格式, 重要的有Unicode.UTF.ISO-8859-1和中国人 ...

  7. Java 字符编码(一)Unicode 字符编码

    Java 字符编码(一)Unicode 字符编码 Unicode(http://www.unicode.org/versions/#TUS_Latest_Version) 是一个编码方案,说白了希望给 ...

  8. 各种字符编码方式详解及由来(ANSI,UNICODE,UTF-8,GB2312,GBK)

    一直对字符的各种编码方式懵懵懂懂,什么ANSI UNICODE UTF-8 GB2312 GBK DBCS UCS……是不是看的很晕,假如您细细的阅读本文你一定可以清晰的理解他们.Let's go! ...

  9. 第48篇 字符编码探密--ASCII,UTF8,GBK,Unicode

    原文地址:http://blog.laofu.online/2017/08/22/encode-string/ ASCII 的由来 在计算机的“原始社会”,有人想把日常的使用的语言使用计算机来表示, ...

随机推荐

  1. Redis分布式锁原理

    1. Redis分布式锁原理 1.1. Redisson 现在最流行的redis分布式锁就是Redisson了,来看看它的底层原理就了解redis是如何使用分布式锁的了 1.2. 原理分析 分布式锁要 ...

  2. js对数组array的常见操作小结

    1.创建数组?两种方式 var arr = new Array("1","2","4"); var arr1 = ["1" ...

  3. docker + gitlab + jenkins 搭建 CI/CD 系统

    gitlab+jenkins+docker 计算机网络大全

  4. SpringCloud学习第二章-SpringBoot

    SpringCloud 学习前提     SpringCloud是基于SpringBoot构建的,因此他延续了SpringBoot的契约模式以及开发方式.下面将讲到SpringBoot的构建方式. S ...

  5. HBase的部署与其它相关组件(Hive和Phoenix)的集成

    HBase的部署与其它相关组件(Hive和Phoenix)的集成 一.HBase部署 1.1.Zookeeper正常部署 首先保证Zookeeper集群的正常部署,并启动之: /opt/module/ ...

  6. 【Linux】linux之如何清理磁盘空间

    相关命令: 1.查询磁盘空间占用情况df -h2.进入根目录,查询大文件与目录 cd /du -sh * | sort -n 查看上GB的目录并且排序,可以用这个命令du -h --max-depth ...

  7. zabbix--监控MySQL主从状态

    zabbix监控MySQL主从状态 搭建MySQL主从后,很多时候不知道从的状态是否ok,有时候出现异常不能及时知道,这里通过shell脚本结合zabbix实现监控并告警 一般情况下,在MySQL的从 ...

  8. linux 管道,输出重定向,后端执行

    1. | (管道) $time|data:"Y-m-d"将前部的输出,作为后部的输入:配合管道使用的命令,典型的就是grep,more find --help | grep cne ...

  9. 团队第四次作业——Alpha1版本发布

    这个作业属于哪个课程 https://edu.cnblogs.com/campus/xnsy/2019autumnsystemanalysisanddesign/ 这个作业要求在哪里 https:// ...

  10. php72w-common conflicts with php-common-5.4.16-46.el7.x86_64

    安装PHP的BC扩展时,报的错. 使用的命令为 yum install php-bcmath 输出错误: --> Processing Conflict: php72w-common--.w7. ...