java 字符编码
java字符编码详细说明
java字符编码详细说明
首先,我们要了解"java字符编码详细说明"所涉及的内容。
Java字符编码主要关注的是如何在Java程序中正确地处理和转换字符数据。
这是因为不同的字符编码可能会影响程序如何解释和呈现文本数据。
Java提供了多种方式来处理字符编码,以确保数据的正确性。
其中,一些关键的编码方式包括:
1.UTF-8: 这是最常用的编码方式之一,因为它可以表示任何Unicode字符。
UTF-8能够向后兼容ASCII编码,因此它也是互联网上最常用的字符编码。
2.ISO-8859-1: 这是一个西欧语言的字符编码,它使用一个字节来表示一个
字符。
3.GB2312, GBK, GB18030: 这些都是用于表示简体中文字符的编码方式。
当我们处理字符数据时,需要特别注意编码的一致性。
如果源数据的编码方式和目标数据的编码方式不匹配,可能会导致乱码或其他不可预测的行为。
为了避免这种情况,我们可以在读取和写入文件、网络传输、数据库操作等操作时指定正确的字符编码。
总结来说,"java字符编码详细说明"主要关注的是如何在Java程序中正确处理和转换字符数据,特别是如何处理不同编码之间的转换以及如何确保编码的一致性。
java中的字符编码方式
java中的字符编码⽅式1. 问题由来⾯试的时候被问到了各种编码⽅式的区别,结果⼀脸懵逼,这个地⽅集中学习⼀下。
2. ⼏种字符编码的⽅式1. ASCII码我们知道,在计算机内部,所有的信息最终都表⽰为⼀个⼆进制的字符串。
每⼀个⼆进制位(bit)有0和1两种状态,因此⼋个⼆进制位就可以组合出256种状态,这被称为⼀个字节(byte)。
也就是说,⼀个字节⼀共可以⽤来表⽰256种不同的状态,每⼀个状态对应⼀个符号,就是256个符号,从0000000到11111111。
上个世纪60年代,美国制定了⼀套字符编码,对英语字符与⼆进制位之间的关系,做了统⼀规定。
这被称为ASCII码,⼀直沿⽤⾄今。
ASCII码⼀共规定了128个字符的编码,⽐如空格"SPACE"是32(⼆进制00100000),⼤写的字母A是65(⼆进制01000001)。
这128个符号(包括32个不能打印出来的控制符号),只占⽤了⼀个字节的后⾯7位,最前⾯的1位统⼀规定为0。
0~31 是控制字符如换⾏回车删除等,32~126 是打印字符,可以通过键盘输⼊并且能够显⽰出来。
2、⾮ASCII编码英语⽤128个符号编码就够了,但是⽤来表⽰其他语⾔,128个符号是不够的。
⽐如,在法语中,字母上⽅有注⾳符号,它就⽆法⽤ASCII码表⽰。
于是,⼀些欧洲国家就决定,利⽤字节中闲置的最⾼位编⼊新的符号。
⽐如,法语中的é的编码为130(⼆进制10000010)。
这样⼀来,这些欧洲国家使⽤的编码体系,可以表⽰最多256个符号。
但是,这⾥⼜出现了新的问题。
不同的国家有不同的字母,因此,哪怕它们都使⽤256个符号的编码⽅式,代表的字母却不⼀样。
⽐如,130在法语编码中代表了é,在希伯来语编码中却代表了字母Gimel (ג),在俄语编码中⼜会代表另⼀个符号。
但是不管怎样,所有这些编码⽅式中,0—127表⽰的符号是⼀样的,不⼀样的只是128—255的这⼀段。
java字符集编码
在java应用软件中,会有多处涉及到字符集编码,有些地方需要进行正确的设置,有些地方需要进行一定程度的处理。
1. getBytes(charset)这是java字符串处理的一个标准函数,其作用是将字符串所表示的字符按照charset编码,并以字节方式表示。
注意字符串在java内存中总是按unicode编码存储的。
比如"中文",正常情况下(即没有错误的时候)存储为"4e2d 6587",如果charset为"gbk",则被编码为"d6d0 cec4",然后返回字节"d6 d0 ce c4".如果charset为"utf8"则最后是"e4 b8 ad e6 96 87".如果是"iso8859-1",则由于无法编码,最后返回"3f 3f"(两个问号)。
java .class类的编码为:unicode;windows 默认的编码为:中文:gb2312; 英文:iso8859;[java]view plaincopyprint?1.String str = "张三" ;2.byte[] jiema= str.getBytes("gb2312") ; //解码3.String bianma = new String(jiema,"UTF-8");//编码如果上面的解码不对可能出现问题2. new String(charset)这是java字符串处理的另一个标准函数,和上一个函数的作用相反,将字节数组按照charset编码进行组合识别,最后转换为unicode存储。
参考上述getBytes的例子,"gbk" 和"utf8"都可以得出正确的结果"4e2d 6587",但iso8859-1最后变成了"003f 003f"(两个问号)。
JAVA字符编码系列_详细解释
JAV A字符编码系列一:Unicode,GBK,GB2312,UTF-8概念基础收藏这两天抽时间又总结/整理了一下各种编码的实际编码方式,和在Java应用中的使用情况,在这里记录下来以便日后参考。
为了构成一个完整的对文字编码的认识和深入把握,以便处理在Java开发过程中遇到的各种问题,特别是乱码问题,我觉得组成一个系列来描述和分析更好一些,包括三篇文章:第一篇:JAV A字符编码系列一:Unicode,GBK,GB2312,UTF-8概念基础第二篇:JAV A字符编码系列二:Unicode,ISO-8859,GBK,UTF-8编码及相互转换第三篇:JAV A字符编码系列三:Java应用中的编码问题第一篇:JA V A字符编码系列一:Unicode,GBK,GB2312,UTF-8概念基础Unicode:制定的编码机制,要将全世界常用文字都函括进去.在1.0中是16位编码,由U+0000到U+FFFF.每个2byte码对应一个字符;在2.0开始抛弃了16位限制,原来的16位作为基本位平面,另外增加了16个位平面,相当于20位编码,编码范围0到0x10FFFF.UCS:ISO制定的ISO10646标准所定义的Universal Character Set,采用4byte编码.Unicode与UCS的关系:ISO与是两个不同的组织,因此最初制定了不同的标准;但自从unicode2.0开始, unicode采用了与ISO10646-1相同的字库和字码,ISO也承诺ISO10646将不会给超出0x10FFFF的UCS-4编码赋值,使得两者保持一致.UCS的编码方式:UCS-2,与unicode的2byte编码基本一样.UCS-4,4byte编码,目前是在UCS-2前加上2个全零的byte.UTF:Unicode/UCS Transformation FormatUTF-8,8bit编码,ASCII不作变换,其他字符做变长编码,每个字符1-3byte.通常作为外码.有以下优点:*与CPU字节顺序无关,可以在不同平台之间交流*容错能力高,任何一个字节损坏后,最多只会导致一个编码码位损失,不会链锁错误(如GB码错一个字节就会整行乱码)UTF-16,16bit编码,是变长码,大致相当于20位编码,值在0到0x10FFFF之间,基本上就是unicode编码的实现.它是变长码,与CPU字序有关,但因为最省空间,常作为网络传输的外码.UTF-16是unicode的preferred encoding.UTF-32,仅使用了unicode范围(0到0x10FFFF)的32位编码,相当于UCS-4的子集.UTF与unicode的关系:Unicode是一个字符集,可以看作为内码.而UTF是一种编码方式,它的出现是因为unicode不适宜在某些场合直接传输和处理. UTF-16直接就是unicode编码,没有变换,但它包含了0x00在编码内,头256字节码的第一个byte都是0x00,在操作系统(C语言)中有特殊意义,会引起问题.采用UTF-8编码对unicode的直接编码作些变换可以避免这问题,并带来一些优点.中国国标编码:GB13000:完全等同于ISO10646-1/Unicode2.1,今后也将随ISO10646/Unicode的标准更改而同步更改.GBK:对GB2312的扩充,以容纳GB2312字符集范围以外的Unicode2.1的统一汉字部分,并且增加了部分unicode中没有的字符.GB18030-2000:基于GB13000,作为Unicode3.0的GBK扩展版本,覆盖了所有unicode编码,地位等同于UTF-8,UTF-16,是一种unicode编码形式.变长编码,用单字节/双字节/4字节对字符编码.GB18030向下兼容GB2312/GBK.GB18030是中国所有非手持/嵌入式计算机系统的强制实施标准.-------------------------------什么是UCS和ISO10646?国际标准ISO10646定义了通用字符集(Universal Character Set,UCS).UCS是所有其他字符集标准的一个超集.它保证与其他字符集是双向兼容的.就是说,如果你将任何文本字符串翻译到UCS格式,然后再翻译回原编码,你不会丢失任何信息.UCS包含了用于表达所有已知语言的字符.不仅包括拉丁语,希腊语,斯拉夫语,希伯来语,阿拉伯语,亚美尼亚语和乔治亚语的描述,还包括中文,日文和韩文这样的象形文字,以及平假名,片假名,孟加拉语,旁遮普语果鲁穆奇字符(Gurmukhi),泰米尔语,印.埃纳德语(Kannada),Malayalam,泰国语,老挝语,汉语拼音(Bopomofo),Hangul,Devangari,Gujarati, Oriya,Telugu以及其他数也数不清的语.对于还没有加入的语言,由于正在研究怎样在计算机中最好地编码它们,因而最终它们都将被加入.这些语言包括Tibetian,高棉语,Runic(古代北欧文字),埃塞俄比亚语,其他象形文字,以及各种各样的印-欧语系的语言,还包括挑选出来的艺术语言比如Tengwar,Cirth和克林贡语(Klingon).UCS还包括大量的图形的,印刷用的,数学用的和科学用的符号,包括所有由TeX,Postscript,MS-DOS,MS-Windows, Macintosh,OCR字体,以及许多其他字处理和出版系统提供的字符.ISO10646定义了一个31位的字符集.然而,在这巨大的编码空间中,迄今为止只分配了前65534个码位(0x0000到0xFFFD).这个UCS的16位子集称为基本多语言面(Basic Multilingual Plane,BMP).将被编码在16位BMP以外的字符都属于非常特殊的字符(比如象形文字),且只有专家在历史和科学领域里才会用到它们.按当前的计划,将来也许再也不会有字符被分配到从0x000000到0x10FFFF这个覆盖了超过100万个潜在的未来字符的21位的编码空间以外去了.ISO10646-1标准第一次发表于1993年,定义了字符集与BMP中内容的架构.定义BMP以外的字符编码的第二部分ISO10646-2正在准备中,但也许要过好几年才能完成.新的字符仍源源不断地加入到BMP中,但已经存在的字符是稳定的且不会再改变了.UCS不仅给每个字符分配一个代码,而且赋予了一个正式的名字.表示一个UCS或Unicode值的十六进制数,通常在前面加上"U+",就象U+0041代表字符"拉丁大写字母A".UCS字符U+0000到U+007F与US-ASCII(ISO646)是一致的,U+0000到U+00FF 与ISO8859-1(Latin-1)也是一致的.从U+E000到U+F8FF,已经BMP以外的大范围的编码是为私用保留的.什么是组合字符?UCS里有些编码点分配给了组合字符.它们类似于打字机上的无间隔重音键.单个的组合字符不是一个完整的字符.它是一个类似于重音符或其他指示标记,加在前一个字符后面.因而,重音符可以加在任何字符后面.那些最重要的被加重的字符,就象普通语言的正字法(orthographies of common languages)里用到的那种,在UCS里都有自己的位置,以确保同老的字符集的向后兼容性.既有自己的编码位置,又可以表示为一个普通字符跟随一个组合字符的被加重字符,被称为预作字符(precomposed characters).UCS里的预作字符是为了同没有预作字符的旧编码,比如ISO8859,保持向后兼容性而设的.组合字符机制允许在任何字符后加上重音符或其他指示标记,这在科学符号中特别有用,比如数学方程式和国际音标字母,可能会需要在一个基本字符后组合上一个或多个指示标记.组合字符跟随着被修饰的字符.比如,德语中的元音变音字符("拉丁大写字母A加上分音符"),既可以表示为UCS码U+00C4的预作字符,也可以表示成一个普通"拉丁大写字母A"跟着一个"组合分音符":U+0041U+0308这样的组合.当需要堆叠多个重音符,或在一个基本字符的上面和下面都要加上组合标记时,可以使用多个组合字符.比如在泰国文中,一个基本字符最多可加上两个组合字符.什么是UCS实现级别?不是所有的系统都需要支持象组合字符这样的UCS里所有的先进机制.因此ISO10646指定了下列三种实现级别:级别1不支持组合字符和Hangul Jamo字符(一种特别的,更加复杂的韩国文的编码,使用两个或三个子字符来编码一个韩文音节)级别2类似于级别1,但在某些文字中,允许一列固定的组合字符(例如,希伯来文,阿拉伯文, Devangari,孟加拉语,果鲁穆奇语,Gujarati,Oriya,泰米尔语,Telugo,印.埃纳德语, Malayalam,泰国语和老挝语).如果没有这最起码的几个组合字符,UCS就不能完整地表达这些语言.级别3支持所有的UCS字符,例如数学家可以在任意一个字符上加上一个tilde(颚化符号,西班牙语字母上面的~)或一个箭头(或两者都加).什么是Unicode?历史上,有两个独立的,创立单一字符集的尝试.一个是国际标准化组织(ISO)的ISO10646项目,另一个是由(一开始大多是美国的)多语言软件制造商组成的协会组织的Unicode项目.幸运的是,1991年前后,两个项目的参与者都认识到,世界不需要两个不同的单一字符集.它们合并双方的工作成果,并为创立一个单一编码表而协同工作.两个项目仍都存在并独立地公布各自的标准,但Unicode协会和ISO/IEC JTC1/SC2都同意保持Unicode和ISO10646标准的码表兼容,并紧密地共同调整任何未来的扩展.那么Unicode和ISO10646不同在什么地方?Unicode协会公布的Unicode标准严密地包含了ISO10646-1实现级别3的基本多语言面.在两个标准里所有的字符都在相同的位置并且有相同的名字.Unicode标准额外定义了许多与字符有关的语义符号学,一般而言是对于实现高质量的印刷出版系统的更好的参考.Unicode详细说明了绘制某些语言(比如阿拉伯语)表达形式的算法,处理双向文字(比如拉丁与希伯来文混合文字)的算法和排序与字符串比较所需的算法,以及其他许多东西.另一方面,ISO10646标准,就象广为人知的ISO8859标准一样,只不过是一个简单的字符集表.它指定了一些与标准有关的术语,定义了一些编码的别名,并包括了规范说明,指定了怎样使用UCS连接其他ISO标准的实现,比如ISO6429和ISO2022.还有一些与ISO紧密相关的,比如ISO14651是关于UCS字符串排序的.考虑到Unicode标准有一个易记的名字,且在任何好的书店里的Addison-Wesley里有,只花费ISO版本的一小部分,且包括更多的辅助信息,因而它成为使用广泛得多的参考也就不足为奇了.然而,一般认为,用于打印ISO10646-1标准的字体在某些方面的质量要高于用于打印Unicode2.0的.专业字体设计者总是被建议说要两个标准都实现,但一些提供的样例字形有显著的区别.ISO10646-1标准同样使用四种不同的风格变体来显示表意文字如中文,日文和韩文(CJK),而Unicode2.0的表里只有中文的变体.这导致了普遍的认为Unicode对日本用户来说是不可接收的传说,尽管是错误的.什么是UTF-8?首先UCS和Unicode只是分配整数给字符的编码表.现在存在好几种将一串字符表示为一串字节的方法.最显而易见的两种方法是将Unicode文本存储为2个或4个字节序列的串.这两种方法的正式名称分别为UCS-2和UCS-4.除非另外指定,否则大多数的字节都是这样的(Bigendian convention).将一个ASCII或Latin-1的文件转换成UCS-2只需简单地在每个ASCII字节前插入0x00.如果要转换成UCS-4,则必须在每个ASCII字节前插入三个0x00.在Unix下使用UCS-2(或UCS-4)会导致非常严重的问题.用这些编码的字符串会包含一些特殊的字符,比如'\0'或'/',它们在文件名和其他C库函数参数里都有特别的含义.另外,大多数使用ASCII文件的UNIX下的工具,如果不进行重大修改是无法读取16位的字符的.基于这些原因,在文件名,文本文件,环境变量等地方,UCS-2不适合作为Unicode的外部编码.在ISO10646-1Annex R和RFC2279里定义的UTF-8编码没有这些问题.它是在Unix 风格的操作系统下使用Unicode的明显的方法.UTF-8有一下特性:UCS字符U+0000到U+007F(ASCII)被编码为字节0x00到0x7F(ASCII兼容).这意味着只包含7位ASCII字符的文件在ASCII和UTF-8两种编码方式下是一样的.所有>U+007F的UCS字符被编码为一个多个字节的串,每个字节都有标记位集.因此, ASCII字节(0x00-0x7F)不可能作为任何其他字符的一部分.表示非ASCII字符的多字节串的第一个字节总是在0xC0到0xFD的范围里,并指出这个字符包含多少个字节.多字节串的其余字节都在0x80到0xBF范围里.这使得重新同步非常容易,并使编码无国界,且很少受丢失字节的影响.可以编入所有可能的231个UCS代码UTF-8编码字符理论上可以最多到6个字节长,然而16位BMP字符最多只用到3字节长.Bigendian UCS-4字节串的排列顺序是预定的.字节0xFE和0xFF在UTF-8编码中从未用到.下列字节串用来表示一个字符.用到哪个串取决于该字符在Unicode中的序号.U-00000000-U-0000007F:0xxxxxxxU-00000080-U-000007FF:110xxxxx10xxxxxxU-00000800-U-0000FFFF:1110xxxx10xxxxxx10xxxxxxU-00010000-U-001FFFFF:11110xxx10xxxxxx10xxxxxx10xxxxxxU-00200000-U-03FFFFFF:111110xx10xxxxxx10xxxxxx10xxxxxx10xxxxxxU-04000000-U-7FFFFFFF:1111110x10xxxxxx10xxxxxx10xxxxxx10xxxxxx10xxxxxxxxx的位置由字符编码数的二进制表示的位填入.越靠右的x具有越少的特殊意义.只用最短的那个足够表达一个字符编码数的多字节串.注意在多字节串中,第一个字节的开头"1"的数目就是整个串中字节的数目.例如:Unicode字符U+00A9=10101001(版权符号)在UTF-8里的编码为:1100001010101001=0xC20xA9而字符U+2260=0010001001100000(不等于)编码为:111000101000100110100000=0xE20x890xA0这种编码的官方名字拼写为UTF-8,其中UTF代表UCS Transformation Format.请勿在任何文档中用其他名字(比如utf8或UTF_8)来表示UTF-8,当然除非你指的是一个变量名而不是这种编码本身.什么编程语言支持Unicode?在大约1993年之后开发的大多数现代编程语言都有一个特别的数据类型,叫做Unicode/ISO10646-1字符.在Ada95中叫Wide_Character,在Java中叫char.ISO C也详细说明了处理多字节编码和宽字符(wide characters)的机制,1994年9月Amendment1to ISO C发表时又加入了更多.这些机制主要是为各类东亚编码而设计的,它们比处理UCS所需的要健壮得多.UTF-8是ISO C标准调用多字节字符串的编码的一个例子,wchar_t类型可以用来存放Unicode字符.第二篇:JA V A字符编码系列二:Unicode,ISO-8859-1,GBK,UTF-8编码及相互转换1、函数介绍在Java中,字符串用统一的Unicode编码,每个字符占用两个字节,与编码有关的两个主要函数为:1)将字符串用指定的编码集合解析成字节数组,完成Unicode-〉charsetName转换public byte[]getBytes(String charsetName)throws UnsupportedEncodingException2)将字节数组以指定的编码集合构造成字符串,完成charsetName-〉Unicode转换public String(byte[]bytes,String charsetName)throws UnsupportedEncodingException2、Unicode与各编码之间的直接转换下面以对中文字符串"a中文"的编码转换为例,来了解各种编码之间的转换1)Unicode和GBK测试结果如下,每个汉字转换为两个字节,且是可逆的,即通过字节可以转换回字符串String-GBK〉ByteArray:\u0061\u4E2D\u6587(a中文)-〉0x610xD60xD00xCE0xC4 ByteArray-GBK〉String:0x610xD60xD00xCE0xC4-〉\u0061\u4E2D\u6587(a中文)2)Unicode和UTF-8测试结果如下,每个汉字转换为三个字节,且是可逆的,即通过字节可以转换回字符串String-UTF-8〉ByteArray:\u0061\u4E2D\u6587(a中文)-〉0x610xE40xB80xAD 0xE6%0x960x87ByteArray-UTF-8〉String:0x610xE40xB80xAD0xE6%0x960x87-〉\u0061\u4E2D\u6587(a中文)3)Unicode和ISO-8859-1测试结果如下,当存在汉字时转换失败,非可逆,即通过字节不能再转换回字符串String-ISO-8859-1〉ByteArray:\u0061\u4E2D\u6587(a中文)-〉0x610x3F0x3F ByteArray-ISO-8859-1〉String:0x610x3F0x3F-〉\u0061\u003F\u003F(a??)3、Unicode与各编码之间的交叉转换在上面直接转换中,由字符串(Unicode)生成的字节数组,在构造回字符串时,使用的是正确的编码集合,如果使用的不是正确的编码集合会怎样呢?会正确构造吗?如果不能正确构造能有办法恢复吗?会信息丢失吗?下面我们就来看看这种情况,这部分可以说明在某些情况下虽然我们最终正确显示了结果,但其间仍然进行了不正确的转换。
java编码
基础概念
字符 字符集(character set)
字符的集合 定义码点与字符的映射关系 例:unicode(统一码),gb2312,ascii等
码点(code point) 码元(code unit) 编码(encoding)
定义码元(code unit)与码点的关系 在unicode之前,其实字符集与编码是确定的,就是说码元与码点是一致的,直到出现了unicode编码后,才有了字符集与编码的概念 字符集与编码关系:
单字节符号:字节第一位设为0,后面7位与unicode码相同,与ASCII码相同。 对于N字节符号(N>1):第一个字节前N位设置为1,第N+1位设置为0,后面字节的前
两位一律为10,剩下的没有提及的二进制位,全是这个符号的unicode码。
编码规则:
UTF-8与unicode的转化
以汉字“严”为例(Unicode->UTF-8):
UNICODE码(统一码)
1990年研发,1994年公布。 只是一个字符集(码表),不是一种编码,比如utf8是unicode的一种编码。 规定了符号的二进制代码,却没有规定如何存储。
UTF-8编码(Unicode Transfer Format)
是一种变长编码,使用1-4字节表示一个符号。 是ASCII的超集,兼容ASCII(使用一字节表示)。 编码规则:
String str = "中国人严";
for(int i = 0; i < str.length();i++) { char c = str.charAt(i); sb.append("\\u" + Integer.toHexString(c));
关于JAVA内存中字符编码的一些说明,x,u,%
关于JAVA内存中字符编码的⼀些说明,x,u,%
1、JAVA中的字符采⽤UTF-16编码,⼀个char只能有两个字节表⽰,其中字符串可以使⽤\u表⽰UTF-16编码的标识
2、JAVA中String的length⽅法返回的是code unit数量,即UTF-16编码之后的字节数(2字节⼀单元)
2、有些地⽅可能有\x这种表⽰,\x标识实际的编码之后的2进制数据的16进制表⽰形式,具体的编码格式则可能有区别,⼀般是属于UTF-8编码之后的字节的16进制表⽰形式
3、作为对⽐Python中,采⽤直接的Unicode码点表⽰,在与⽹络交互的时候则需要转换为具体的UTF-8或者UTF-16等编码形式
4、关于%,⼀般⽤于http请求中路径中的字符转义,具体内容⽐较复杂,参考⼀下这个⽹址,也没深究
总之⼀句话,不讲编码的转化都是耍流氓
参考链接。
java 常用编码格式
java 常用编码格式
Java 中常用的编码格式有:
1.UTF-8:UTF-8 是 Java 的默认编码格式,也是目前使用最广泛的编码格式之一。
它是一种可变长度的编码方式,支持几乎所有的国家和地区字符。
2.GB2312:GB2312 是中国制定的国家标准编码,用于表示简体中文。
3.GBK:GBK 是 GB2312 的扩展,支持繁体中文和部分其他字符集。
4.ISO-8859-1:ISO-8859-1 是西欧语言的编码标准,支持包括英文在内的多种语言。
5.BIG5:BIG5 是中国台湾地区制定的国家标准编码,用于表示繁体中文。
在 Java 中,可以通过以下方式获取和设置编码格式:
java复制代码
// 获取默认编码格式
String defaultEncoding = System.getProperty("file.encoding");
// 设置编码格式
OutputStream outputStream = new FileOutputStream("file.txt");
outputStream.write(bytes, 0, bytes.length,
Charset.forName("UTF-8"));
其中,System.getProperty("file.encoding")可以获取 JVM 启动时设置的默认编码格式;Charset.forName("UTF-8")可以指定特定的编码格式,此处为 UTF-8。
java 使用的编码逻辑
java 使用的编码逻辑Java 使用的编码逻辑主要涉及以下几个方面:1. 字符编码Java 中的字符编码采用的是Unicode 编码,它支持世界上几乎所有的字符集,包括ASCII、Latin-1、中文、日文、韩文等等。
Java 中的char 类型占用两个字节,因此它可以表示Unicode 编码中的任意一个字符。
2. 字符串编码Java 中的字符串编码也采用的是Unicode 编码,但在存储和传输过程中,需要将Unicode 编码转换成其他编码格式,如UTF-8、UTF-16 等。
Java 中的字符串类型String 采用的是UTF-16 编码,因此在进行字符串操作时,需要将其他编码格式的字符串转换成UTF-16 编码。
3. 文件编码Java 中的文件编码也需要考虑字符编码和字符串编码的问题。
在读取和写入文件时,需要指定文件的编码格式,以确保文件内容的正确性。
常用的文件编码格式包括ASCII、UTF-8、UTF-16 等。
4. 数据库编码Java 中的数据库编码也需要考虑字符编码和字符串编码的问题。
在使用JDBC 连接数据库时,需要指定数据库的编码格式,以确保数据的正确性。
常用的数据库编码格式包括ASCII、UTF-8、UTF-16 等。
5. 网络编码Java 中的网络编码也需要考虑字符编码和字符串编码的问题。
在进行网络通信时,需要将数据转换成字节流进行传输。
在传输过程中,需要指定数据的编码格式,以确保数据的正确性。
常用的网络编码格式包括ASCII、UTF-8、UTF-16 等。
总之,Java 中的编码逻辑涉及到字符编码、字符串编码、文件编码、数据库编码和网络编码等多个方面,需要在不同的场景下进行适当的配置和转换,以确保数据的正确性和可靠性。
java字符集编码
ASCII(American Standard Code for Information Interchange,美国信息互换标准代码),是基于常用的英文字符的一套电脑编码系统。
我们知道英文中经常使用的字符、数字符号被计算机处理时都是以二进制码的形式出现的。
这种二进制码的集合就是所谓的ASCII码。
每一个ASCII码与一个8位(bit)二进制数对应。
其最高位是0,相应的十进制数是0-127。
如,数字“0”的编码用十进制数表示就是48。
另有128个扩展的ASCII码,最高位都是1,由一些制表符和其它符号组成。
ASCII是现今最通用的单字节编码系统。
GB2312:GB2312码是中华人民共和国国家汉字信息交换用编码,全称《信息交换用汉字编码字符集-基本集》。
主要用于给每一个中文字符指定相应的数字,也就是进行编码。
一个中文字符用两个字节的数字来表示,为了和ASCII码有所区别,将中文字符每一个字节的最高位置都用1来表示。
GBK:为了对更多的字符进行编码,国家又发布了新的编码系统GBK(GBK的K是“扩展”的汉语拼音第一个字母)。
在新的编码系统里,除了完全兼容GB2312 外,还对繁体中文、一些不常用的汉字和许多符号进行了编码。
ISO-8859-1:是西方国家所使用的字符编码集,是一种单字节的字符集,而英文实际上只用了其中数字小于128的部分。
Unicode:这是一种通用的字符集,对所有语言的文字进行了统一编码,对每一个字符都用2个字节来表示,对于英文字符采取前面加“0”字节的策略实现等长兼容。
如“a” 的ASCII码为0x61,UNICODE 就为0x00,0x61。
UTF-8:Eight-bit UCS Transformation Format,(UCS,Universal Character Set,通用字符集,UCS 是所有其他字符集标准的一个超集)。
一个7位的ASCII码值,对应的UTF码是一个字节。
java常用编码格式
java常用编码格式Java 中常用的编码格式有以下几种:1. UTF-8:UTF-8 是一种变长字符编码,支持世界上几乎所有语言的字符集,是目前最常用的编码格式之一。
2. GBK:GBK 是针对简体中文的一种编码格式,它支持简体中文中的常用字符集,但不支持繁体中文和其他少数民族语言。
3. Shift-JIS:Shift-JIS 是一种针对日文、韩文等西文字符集的编码格式,它可以支持中文字符集的编码。
4. 16-bit 编码:16-bit 编码是一种用于在计算机内部存储多字节字符的编码格式,它将一个多字节字符转换为 16 个 ASCII 字符(0-F)。
这种编码格式在处理大量数据时可以显著减少内存占用。
5. 8-bit 编码:8-bit 编码是一种用于在计算机内部存储单字节字符的编码格式,它将一个单字节字符转换为 8 个 ASCII 字符(0-7)。
这种编码格式在处理少量数据时可以显著减少内存占用。
需要注意的是,在 Java 中,不同的字符集需要使用不同的字符编码格式进行转换。
在进行字符串操作时,应该使用正确的字符编码格式,否则可能会出现乱码等问题。
Java 中常用的编码格式有以下几种:1. UTF-8:UTF-8 是一种变长字符编码,支持世界上几乎所有语言的字符集,是目前最常用的编码格式之一。
2. GBK:GBK 是针对简体中文的一种编码格式,它支持简体中文中的常用字符集,但不支持繁体中文和其他少数民族语言。
3. Shift-JIS:Shift-JIS 是一种针对日文、韩文等西文字符集的编码格式,它可以支持中文字符集的编码。
4. 16-bit 编码:16-bit 编码是一种用于在计算机内部存储多字节字符的编码格式,它将一个多字节字符转换为 16 个ASCII 字符(0-F)。
这种编码格式在处理大量数据时可以显著减少内存占用。
5. 8-bit 编码:8-bit 编码是一种用于在计算机内部存储单字节字符的编码格式,它将一个单字节字符转换为 8 个 ASCII 字符(0-7)。
JAVA字符编码:Unicode,ISO-8859-1,GBK,UTF-8编码及相互转换
【适用范围】适用EOS所有版本,操作系统不限,数据库不限【问题描述和定位】JAVA字符编码:Unicode,ISO-8859-1,GBK,UTF-8编码及相互转换【解决方案和步骤】1、函数介绍在Java中,字符串用统一的Unicode编码,每个字符占用两个字节,与编码有关的两个主要函数为:1)将字符串用指定的编码集合解析成字节数组,完成Unicode-〉charsetName转换public byte[] getBytes(String charsetName) throws UnsupportedEncodingException2)将字节数组以指定的编码集合构造成字符串,完成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 0xE 6%0x96 0x87ByteArray-UTF-8〉String:0x61 0xE4 0xB8 0xAD 0xE6%0x96 0x87-〉\u0061\u4E2D\u6 587(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)生成的字节数组,在构造回字符串时,使用的是正确的编码集合,如果使用的不是正确的编码集合会怎样呢?会正确构造吗?如果不能正确构造能有办法恢复吗?会信息丢失吗?下面我们就来看看这种情况,这部分可以说明在某些情况下虽然我们最终正确显示了结果,但其间仍然进行了不正确的转换。
java常用编码格式
java常用编码格式
在Java中,常用的编码格式有以下几种:
1. UTF-8:它是一种可变长度的Unicode字符编码,它可以使用1到4个字节表示一个字符,是最常用的编码格式之一。
它支持全球范围内的大部分字符集,包括中文、日文、韩文等。
2. ISO-8859-1:它是Latin-1字符集的编码方式,它支持欧洲大部分语言的字符。
它是一个单字节编码,每个字符占用一个字节。
但是它并不支持中文等非拉丁字符。
3. GBK/GB2312:它是中文字符集的编码方式,它支持简体中文字符集。
GBK是GB2312的扩展,支持更多的字符。
它是一个双字节编码,每个中文字符占两个字节,英文字符占用一个字节。
4. UTF-16:它是Unicode字符集的编码方式,它支持大部分字符集,包括中文、日文、韩文等。
UTF-16是一个固定长度的编码方式,每个字符占用2个字节。
这些编码格式可以通过Java的字符串类型来表示和处理。
在Java中,字符串类型使用的是UTF-16编码格式,它是Java默认的编码方式。
如果需要在Java中处理其他编码格式的字符串,可以使用相关的编码、解码函数来转换。
例如,可以使用`getBytes()`方法将字符串转换为指定的编码格式字节数组,使用`new String()`方法将字节数组按照指定的编码格式转换为字符串。
Java字符集和编码
Java字符集和编码为什么要讲字符集?1.Java采用Unicode编码,char型变量是16位的Unicode编码;2.加深对java.io包里面的字节流/字符流的理解;3.理解和解决Java编程中的乱码问题。
一.ASCII编码是由美国国家标准局(ANSI)制定的ASCII码(American Standard Code for Information Interchange,美国标准信息交换码),它已被国际标准化组织(ISO)定为国际标准,称为ISO 646标准。
适用于所有拉丁文字字母,ASCII码有7位码和8位码两种形式。
1.7位ASCII码第0~32号及第127号(共34个)是控制字符或通讯专用字符,如控制符:LF(换行)、CR(回车)、FF(换页)、DEL(删除)、BEL(振铃)等;通讯专用字符:SOH(文头)、EOT(文尾)、ACK(确认)等;第33~126号(共94个)是字符,其中第48~57号为0~9十个阿拉伯数字;65~90号为26个大写英文字母,97~122号为26个小写英文字母,其余为一些标点符号、运算符号等。
2.8位ASCII码但是,很多国家用的不是英文,他们的字母里有许多是ASCII里没有的,为了可以在计算机保存他们的文字,他们决定采用127号之后的空位来表示这些新的字母、符号,还加入了很多画表格时需要用下到的横线、竖线、交叉等形状,一直把序号编到了最后一个状态255。
从128到255这一页的字符集被称"扩展ASCII(8位ASCII码)"。
二.双字节字符集(Double Byte Charecter Set, DBCS)GB2312-GBK 在DBCS系列标准里,最大的特点是两字节长的汉字字符和一字节长的英文字符并存于同一套编码方案里,因此他们写的程序为了支持中文处理,必须要注意字串里的每一个字节的值,如果这个值是大于127的,那么就认为一个双字节字符集里的字符出现了。
Java字符编码知识简介
Java字符编码知识简介字符(Character):是文字与符号的总称,包括文字、图形符号、数学符号等。
l 字符集(Charset):就是一组抽象字符的集合。
字符集常常和一种具体的语言文字对应起来,该文字中的所有字符或者大部分常用字符就构成了该文字的字符集,比如英文字符集。
一组有共同特征的字符也可以组成字符集,比如繁体汉字字符集、日文汉字字符集。
字符集的子集也是字符集。
计算机要处理各种字符,就需要将字符和二进制内码对应起来,这种对应关系就是字符编码(Encoding):制定编码首先要确定字符集,并将字符集内的字符排序,然后和二进制数字对应起来。
根据字符集内字符的多少,会确定用几个字节来编码。
每种编码都限定了一个明确的字符集合,叫做被编码过的字符集(Coded Character Set),这是字符集的另外一个含义。
通常所说的字符集大多是这个含义。
常用字符集有哪些?ASCII:American Standard Code for Information Interchange,美国信息交换标准码。
目前计算机中用得最广泛的字符集及其编码,由美国国家标准局(ANSI)制定。
它已被国际标准化组织(ISO)定为国际标准,称为ISO 646标准。
ASCII字符集由控制字符和图形字符组成。
在计算机的存储单元中,一个ASCII码值占一个字节(8个二进制位),其最高位(b7)用作奇偶校验位。
所谓奇偶校验,是指在代码传送过程中用来检验是否出现错误的一种方法,一般分奇校验和偶校验两种。
奇校验规定:正确的代码一个字节中1的个数必须是奇数,若非奇数,则在最高位b7添1。
偶校验规定:正确的代码一个字节中1的个数必须是偶数,若非偶数,则在最高位b7添1。
ISO 8859-1:全称ISO/IEC 8859,是国际标准化组织(ISO)及国际电工委员会(IEC)联合制定的一系列8位字符集的标准,现时定义了15个字符集。
ASCII收录了空格及94个“可印刷字符”,足以给英语使用。
Java字符编码原理
Eclipse编写代码设置为UTF-8如果要使插件开发应用能有更好的国际化支持,能够最大程度的支持中文输出,则最好使Java文件使用UTF-8编码。
然而,Eclipse工作空间(workspace)的缺省字符编码是操作系统缺省的编码,简体中文操作系统(Windows XP、Windows2000简体中文)的缺省编码是GB18030,在此工作空间中建立的工程编码是GB18030,工程中建立的java文件也是GB18030。
如果要使新建立工程、java文件直接使UTF-8则需要做以下工作:1、windows->Preferences...打开"首选项"对话框,左侧导航树,导航到general->Workspace,右侧Text file encoding,选择Other,改变为UTF-8,以后新建立工程其属性对话框中的Text fileencoding即为UTF-8。
2、windows->Preferences...打开"首选项"对话框,左侧导航树,导航到general->ContentTypes,右侧Context Types树,点开Text,选择Java Source File,在下面的Defaultencoding输入框中输入UTF-8,点Update,则设置Java文件编码为UTF-8。
其他java应用开发相关的文件如:properties、XML等已经由Eclipse缺省指定,分别为ISO8859-1,UTF-8,如开发中确需改变编码格式则可以在此指定。
3、经过上述两步,新建java文件即为UTF-8编码,Eclipse编译、运行、调试都没问题,但是做RCP应用的Product输出时、或者插件输出时,则总是出错,要么不能编译通过(输出时要重新compile)、要么输出的插件运行时中文显示乱码。
此时需要再RCP应用、或插件Plugin工程的build.properties中增加一行,javacDefaultEncoding.. =UTF-8。
JAVA编码之 ASCII、Unicode、GBK和UTF-8字符编码的区别联系
/xiaohulunb/article/details/39588005开始计算机只在美国用。
八位的字节一共可以组合出256(2的8次方)种不同的状态。
他们把其中的编号从0开始的32种状态分别规定了特殊的用途,一但终端、打印机遇上约定好的这些字节被传过来时,就要做一些约定的动作。
遇上0×10, 终端就换行,遇上0×07, 终端就向人们嘟嘟叫,例好遇上0x1b, 打印机就打印反白的字,或者终端就用彩色显示字母。
他们看到这样很好,于是就把这些0×20以下的字节状态称为”控制码”。
他们又把所有的空格、标点符号、数字、大小写字母分别用连续的字节状态表示,一直编到了第127号,这样计算机就可以用不同字节来存储英语的文字了。
大家看到这样,都感觉很好,于是大家都把这个方案叫做ANSI 的”Ascii”编码(American Standard Code for Information Interchange,美国信息互换标准代码)。
当时世界上所有的计算机都用同样的ASCII方案来保存英文文字。
后来,就像建造巴比伦塔一样,世界各地的都开始使用计算机,但是很多国家用的不是英文,他们的字母里有许多是ASCII里没有的,为了可以在计算机保存他们的文字,他们决定采用127号之后的空位来表示这些新的字母、符号,还加入了很多画表格时需要用下到的横线、竖线、交叉等形状,一直把序号编到了最后一个状态255。
从128 到255这一页的字符集被称”扩展字符集“。
从此之后,贪婪的人类再没有新的状态可以用了,美帝国主义可能没有想到还有第三世界国家的人们也希望可以用到计算机吧!等中国人们得到计算机时,已经没有可以利用的字节状态来表示汉字,况且有6000多个常用汉字需要保存呢。
但是这难不倒智慧的中国人民,我们不客气地把那些127号之后的奇异符号们直接取消掉, 规定:一个小于127的字符的意义与原来相同,但两个大于127的字符连在一起时,就表示一个汉字,前面的一个字节(他称之为高字节)从0xA1用到0xF7,后面一个字节(低字节)从0xA1到0xFE,这样我们就可以组合出大约7000多个简体汉字了。
java获取字符串编码的方法
java获取字符串编码的方法1.引言1.1 概述概述部分应该对整篇文章进行一个简要的介绍,包括讲述Java获取字符串编码的方法的重要性和必要性。
【概述】在现代计算机系统中,字符串的编码是一个非常重要的概念。
由于不同的编码标准和方式存在,字符串的编码决定了我们如何正确地存储、传输和处理文本数据。
特别是在国际化和跨平台的应用开发中,了解并正确处理字符串编码问题显得尤为重要。
本文旨在介绍如何在Java编程语言中获取字符串的编码。
通过学习本文,读者将能够了解到Java提供的多种方法来获取字符串的编码,并学会如何正确地在日常编码处理中应用这些方法。
首先,我们将简单概述字符串编码的概念,包括字符集、编码方式等基本知识。
随后,我们将详细介绍Java中获取字符串编码的方法,涉及到编码检测、获取默认编码、获取指定编码等方面。
通过这些方法的学习,读者将能够深入理解字符串编码相关的概念和操作,并能够根据实际需求选择合适的方法来获取字符串编码。
在结论部分,我们将对本文进行总结,并给出一些进一步学习和应用的建议。
希望本文能够帮助读者更好地处理字符串编码问题,提高编程效率和代码质量。
让我们首先进入正文,探索Java获取字符串编码的方法。
1.2文章结构1.2 文章结构本文将主要介绍Java中获取字符串编码的方法。
下面是文章的具体结构:2. 正文部分2.1 字符串编码的概念2.2 Java中获取字符串编码的方法在正文部分,我们将首先介绍字符串编码的概念,包括什么是字符串编码以及为什么需要获取字符串编码。
然后,我们将详细讲解Java中获取字符串编码的各种方法。
其中包括使用String类的getBytes()方法获取字符串的字节数组,通过Charset类获取系统默认编码等方法。
我们将对每种方法进行详细说明,并给出相应的示例代码和运行结果。
3. 结论部分3.1 总结在本文中,我们介绍了Java中获取字符串编码的方法。
通过学习本文,读者可以了解到如何使用Java代码来获取字符串的编码信息,以及在实际开发中如何选择合适的方法来获取所需的字符串编码。
java 字符串 utf-8编码原理
在Java编程语言中,字符串的UTF-8编码原理是一个非常重要的概念。
了解UTF-8编码原理可以帮助我们更好地处理和操作字符串,同时也有助于理解计算机中字符编码的工作原理。
在本文中,我将深入探讨Java字符串的UTF-8编码原理,帮助你全面、深刻地理解这一主题。
1. 了解UTF-8编码UTF-8是一种Unicode字符集的可变长度字符编码,它可以表示Unicode标准中的任何字符。
在UTF-8编码中,一个字符的编码长度可以是1个字节到4个字节不等,这取决于字符的Unicode码点范围。
它使用了单字节和多字节编码,可以有效地节省存储空间,同时兼容ASCII字符。
2. Java中字符串的UTF-8编码在Java中,字符串是以UTF-16编码形式存储的,每个字符占用2个字节。
但是,在将字符串输出到文件、网络或进行其他操作时,通常需要使用UTF-8编码。
Java提供了丰富的库函数来进行字符串的UTF-8编码和解码操作,以便我们能够方便地处理字符串的编码转换。
3. 字符串的UTF-8编码转换在Java中,我们可以使用getBytes()函数将字符串转换为UTF-8编码的字节数组。
例如:```javaString str = "Hello, 你好";byte[] utf8Bytes = str.getBytes("UTF-8");```在这个例子中,getBytes("UTF-8")函数将字符串转换成了UTF-8编码的字节数组,我们可以通过该字节数组进行文件输出、网络传输等操作。
4. UTF-8编码的字符长度与字符串长度需要注意的是,UTF-8编码中一个字符的长度并不等同于字符串的长度。
由于UTF-8采用可变长度编码方式,一个字符的长度可能是1到4个字节。
在进行字符串长度计算时,需要考虑字符的实际编码长度,而不是直接使用字符串的长度函数。
5. 个人观点与理解了解Java字符串的UTF-8编码原理对于Java编程开发人员来说是非常重要的。
Java——获取字符串编码格式
Java——获 取 字 符 串 编 码 格 式
判断一个字符的编码格式:
public static String getEncoding(String str) { String encode = "GB2312"; try { if (isEncoding(str, encode)) { // 判断是不是GB2312 return encode; } } catch (Exception exception) { } encode = "ISO-8859-1"; try { if (isEncoding(str, encode)) { // 判断是不是ISO-8859-1 return encode; } } catch (Exception exception1) { } encode = "UTF-8"; try { if (isEncoding(str, encode)) { // 判断是不是UTF-8 return encode; } } catch (Exception exception2) { } encode = "GBK"; try { if (isEncoding(str, encode)) { // 判断是不是GBK return encode; } } catch (Exception exception3) { } return ""; // 如果都不是,说明输入的内容不属于常见的编码格式。
}
public static boolean isEncoding(String str, String encode) { try { if (str.equals(new String(str.getBytes(), encode))) { return true; } } catch (UnsupportedEncodingException e) { e.printStackTrace(); } return false;
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
当我们从文件中读数据时,最好使用InputStream方式,然后采用String(byte[] bytes, String encoding)指明文件的编码方式。不要使用Reader方式,因为Reader方式会自动根据jdk指明的编码方式把文件内容转换成unicode 编码。
我们把浏览器编码叫做 Browser_Charset,把JVM编码叫做JVM_Charset(通常等于服务器系统编码)。
当浏览器的数据过来的时候,是一个带有Browser_Charset的byte[]。
如果用户处理程序需要一个String类型的数据,那么JVM会好心好意地把这个byte[]转换成String。使用的转换器是 JVM_Charset -> Unicode。
从HttpRequest中读参数时,利用reqeust.setCharacterEncoding()方法设置编码方式,读出的内容就是正确的了。
先说Java。
JVM里面的任何字符串资源都是Unicode,就是说,任何String类型的数据都是Unicode编码。没有例外。既然只有一种编码,那么,我们可以这么说,JVM里面的String是不带编码的。String相当于 char[]。
(2) Browser_Charset -> Unicode,把这个还原的byte[]转换成 String。
这个效果,和直接从HTTP Request取得byte[],然后执行 (2) Browser_Charset -> Unicode 的效果是一样的。
二、基本概念
2.1 JAVA中字符的表达
JAVA 中有char、byte、String这几个概念。char 指的是一个UNICODE字符,为16位的整数。byte 是字节,字符串在网络传输或存储前需要转换为byte数组。在从网络接收或从存储设备读取后需要将byte数组转换成String。String是字符串,可以看成是由char组成的数组。String 和 char 为内存形式,byte是网络传输或存储的序列化形式。
byte[] bytesGB2312 = str.getBytes(“GB2312”);
//取得平台缺省编码的字节(solaris为ISO8859_1,windows为GB2312)
byte[] bytesDefault = str.getBytes();
当我们从数据库中读文本数据时,采用ResultSet.getBytes()方法取得字节数组,同样采用带编码方式的字符串构造方法即可。
ResultSet rs;
String str = new String(bytes, "gb2312");
ISO8859_1用来编码拉丁文,它由单字节(0-255)组成。
GB2312、GBK用来编码简体中文,它有单字节和双字节混合组成。最高位为1的字节和下一个字节构成一个汉字,最高位为0的字节是ASCII码。
UTF-8/UTF-16/UTF-32是国际标准UNICODE的编码方式。 用得最多的是UTF-8,主要是因为它在对拉丁文编码时节约空间。
最不容易出现编码问题的地方是数据库和JVM之间。这应该是数据库JDBC连接的基本功能。本文不专门进行讨论。
最容易出问题的地方是浏览器和服务器JVM之间(其实,代码里面的字符串更容易出问题,不过,我已经事先声明,本文不讨论代码中的字符串编码)。下面主要讨论这块浏览器和服务器JVM之间的编码问题。
UNICODE值 UTF-8编码
U-00000000 - U-0000007F: 0xxxxxxx
U-00000080 - U-000007FF: 110xxxxx 10xxxxxx
U-00000800 - U-0000FFFF: 1110xxxx 10xxxxxx 10xxxxxx
举例:
英
String ying = “英”;
char ying = ying.charAt(0);
String yingHex = Integer.toHexString(ying);
82 F1
byte yingGBBytes = ying.getBytes(“GBK”);
//用指定的编码从字节流里面读取字符
InputStream in = xxx;
InputStreamReader reader = InputStreamReader( in, “GB2312”);
char aChar = reader.read();
所以,Unicode是所有编码转换的中间介质。所有的编码都有一个转换器可以转换到Unicode,而Unicode也可以转换到其他所有的编码。这样构成了一个总线结构。
比如,如果总共有10种编码,那么只需要 10 + 10 = 20个转换器就够了。如果要是两两直接转换,那么,需要的转换器数量是一个组合数字,需要90个转换器。
(2) 动态改变:在往response流里面写数据前可以调用response.setContentType(),设定正确的编码类型。
(3) 在TOMCAT中,由Request.getParameter() 得到的参数,编码方式都是ISO8859_1。所以如果在浏览器输入框内输入一个汉字“英”,在服务器端就得到一个ISO8859_1编码的(0x00,0xD3,0x00,0xA2)。所以通常在接收参数时转码:
注意,如果这个时候,Browser_Charset 和 JVM_Charset并不相等。那么,这个自动转换是错误的。
为了弥补这个错误。我们需要做两步工作。
(1) Unicode -> JVM_Charset,把这个String 转换回到原来的 byte[]。
四、JSP、数据库的编码
4.1 JSP中的编码
(1) 静态声明:
CHARSET有两个作用:
JSP文件的编码方式:在读取JSP文件、生成JAVA类时,源JSP文件中汉字的编码
JSP输出流的编码方式:在执行JSP时,往response流里面写入数据的编码方式
有些语言的VM或者解释器的字符串编码可能不同。比如,Ruby。不过,编码转换原理都是一样的。
That is all.
JAVA字符编码
一、概要
在JAVA应用程序特别是基于WEB的程序中,经常遇到字符的编码问题。为了防止出现乱码,首先需要了解JAVA是如何处理字符的,这样就可以有目的地在输入/输出环节中增加必要的转码。其次,由于各种服务器有不同的处理方式,还需要多做试验,确保使用中不出现乱码。
不要采取下面的步骤。
ResultSet rs;
String str = rs.getString();
str = new String(str.getBytes("iso8859-1"), "gb2312");
这种编码转换方式效率底。之所以这么做的原因是,ResultSet在getString()方法执行时,默认数据库里的数据编码方式为 iso8859-1。系统会把数据依照iso8859-1的编码方式转换成unicode。使用str.getBytes("iso8859-1")把数据还原,然后利用new String(bytes, "gb2312")把数据从gb2312转换成unicode,中间多了好多步骤。
如果在Request里面设置了CharacterEncoding,那么POST Data参数就不需要自己手工转换了,web server的自动转换就是正确的。URL的参数编码还涉及到URL编码,需要考虑的问题多一些,没有这么简单。
JVM把数据发到浏览器的时候。也需要考虑编码问题。可以在Response里面设置。另外,HTML Meta Header里面也可以设置编码,提醒Browser选择正确编码。
U-00010000 - U-001FFFFF: 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx
U-00200000 - U-03FFFFFF: 111110xx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
GB编码的字节数值
D3 A2
2.2 编码方式的简介
String序列化成byte数组或反序列化时需要选择正确的编码方式。如果编码方式不正确,就会得到一些0x3F的值。常用的字符编码方式有ISO8859_1、GB2312、GBK、UTF-8/UTF-16/UTF-32。
一个系统的不同部分,都有自己的编码。比如,数据库,文件,JVM,浏览器这4个部分。
在这些部分之间数据交换的地方,就会出现编码问题。比如,数据库和JVM之间,文件和JVM之间,浏览器和JVM之间。这些问题的原理都是相通的。
编码问题最容易处理的地方是文件和JVM之间。文件IO API带有encoding 参数,请自行查阅。
U-04000000 - U-7FFFFFFF: 1111110x 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
三、J2SE中相关的函数
String str =”英”;
//取得GB2312编码的字节
//用指定的编码将字节转换成字符串
String newStrGB = new String(bytesGB2312, “GB2312”);
//用平台缺省的编码将字节转换成字符串(solaris为ISO8859_1,windows为GB2312)
String newStrDefault = new String(bytesDefault);
JVM里面的 byte[] 数据是带编码的。比如,Big5,GBK,GB2312,UTF-8之类的。