ucenter的中文问题终于解决,这也暴露我对Java编码知识的严重不足,经过多次试验和搜索,对这块知识终于有了一个新的认识,所以把理解的内容写道这里

1:JVM的内存中字符串的编码格式是统一的吗?

JVM里面的任何字符串资源都是Unicode,String相当于 char[] 。 而JVM中的byte[]是带编码的,比如,Big5,GBK,GB2312,UTF-8之类的。一个GBK编码的byte[] 转换成 String,

其实就是从GBK编码向Unicode编码转换。一个String转换成一个Big5编码的byte[],其实就是从Unicode编码向Big5编码转换。所以,Unicode是所有编码转换的中间介质。所有的编码都有一个转换器可以转换到Unicode,而Unicode也可以转换到其他所有的编码。

这个做个测试

public class CodeTest {

    @Test
public void test() throws UnsupportedEncodingException {
String str="I am 高兴";
System.out.println(str);
}
}

在debug中显示'高'的值我39640,为该中文字符的unicode的编码,Java中的char是2个字节的。

2:源文件的编码对编译的影响。

这里我专门使用了Javac和Java两个命令来做个这个试验,源码如下:

public class CodeTest
{
public static void main (String[] args)
{
String str="高兴";
System.out.println(str);
}
}

这个源码我在UE里面把他转成GBK的,编译没有问题。但是转成UTF-8格式,就出现了问题:”楂樺叴“ ,

public class CodeTest {

    @Test
public void test() throws UnsupportedEncodingException {
// String str="I am 君山";
// System.out.println(str);
String str="高兴";
str=new String(str.getBytes("UTF-8"),"GBK");
System.out.println(str);
}
}

str的值为”楂樺叴“。说明源文件的编码对编译时有影响的。GBK为本地系统的编码。Javac在编译过程中把UTF-8的转成了GBK.  下面一段是解释:

Java编译器在对源文件编译前,首先会源文件转换为unicode编码,然后再进行编译。例如:我们的源文件是以UTF-8的方式保存的,而在编译时编译器却把它当作是用GBK方式保存的,这样编译器就会按照GBK->Unicode的编码转换方法对源文件进行转换,然后再编译,这样当然会出错,实际上编译器应当按照UTF-8->Unicode的编码转换方法来对源文件进行转换。

常我们手动建立一个java文件Demo.java,并保存。此时Demo.java文件的编码为ANSI,中文操作系统下就是GBK.然后使用javac命令来编译该源文件。”javac Demo.java”。Javac也需要读取java文件,那么javac是使用什么编码来解码我们读取的字节呢?其实javac采用了操作系统默认的GBK编码解码我们读取的字节,这个编码正好也是Demo.java文件的编码,二者一致,所以不会出现乱码情况。让我们来做点手脚,在保存Demo.java文件时,我们选择UTF-8保存。此时Demo.java文件编码就是UTF-8了。我们再使用”javac Demo.java”来编译,如果Demo.java里含有中文字符,此时控制台会出现警告信息,也出现了乱码。究其原因,就是因为javac采用了GBK编码解码我们读取的字节。因为我们的字节是UTF-8编码的,所以会出现乱码。如果不信的话你可以自己试试。那么解决办法呢?解决办法就是使用javac的encoding参数来制定我们的解码编码。如下:javac -encoding UTF-8 Demo.java。这里我们指定了使用UTF-8来解码读取的字节,由于这个编码和Demo.java文件编码一致,所以不会出现乱码情况了。

3:String的编码和解码

String对象的getBytes()可以对字符串进行编码转化成byte数组。

 public static void encode() {
String name = "I am 君山";
toHex(name.toCharArray());
try {
byte[] iso8859 = name.getBytes("ISO-8859-1");
toHex(iso8859);
byte[] gb2312 = name.getBytes("GB2312");
toHex(gb2312);
byte[] gbk = name.getBytes("GBK");
toHex(gbk);
byte[] utf16 = name.getBytes("UTF-16");
toHex(utf16);
byte[] utf8 = name.getBytes("UTF-8");
toHex(utf8);
} catch (UnsupportedEncodingException e) {
e.printStackTrace();
}
}

默认使用系统编码。

String(byte[],charset)这是对字节数组进行解码。这个是经常容易出问题的地方,你使用gbk编码,却使用utf-8解码,那么生成的String的unicode的编码已经变了。字节数组通过编码映射到指定的字符,然后这些字符转成unicode编码转成

解码的黑洞问题:

将中文和中文符号经过不支持中文的 ISO-8859-1 编码后,所有字符变成了“?”,这是因为用 ISO-8859-1 进行编解码时遇到不在码值范围内的字符时统一用 3f 表示,这也就是通常所说的“黑洞”,所有 ISO-8859-1 不认识的字符都变成了“?”。

java的编码问题详解的更多相关文章

  1. Java:编码的详解

    ASCII:美国信息标准信息码,用一个字节的7为表示. ISO8859-1:拉丁码表 欧洲码表 ,用一个字节的8位表示. GB2312:中国的中文编码表. GBK:中国的中文编码表升级,融合了更多的中 ...

  2. Java版人脸检测详解下篇:编码

    欢迎访问我的GitHub https://github.com/zq2599/blog_demos 内容:所有原创文章分类汇总及配套源码,涉及Java.Docker.Kubernetes.DevOPS ...

  3. 国际化,java.util.ResourceBundle使用详解

    java.util.ResourceBundle使用详解   一.认识国际化资源文件   这个类提供软件国际化的捷径.通过此类,可以使您所编写的程序可以:          轻松地本地化或翻译成不同的 ...

  4. java.util.ResourceBundle使用详解

    java.util.ResourceBundle使用详解   一.认识国际化资源文件   这个类提供软件国际化的捷径.通过此类,可以使您所编写的程序可以:          轻松地本地化或翻译成不同的 ...

  5. java.util.ResourceBundle使用详解(转)

    java.util.ResourceBundle使用详解   一.认识国际化资源文件   这个类提供软件国际化的捷径.通过此类,可以使您所编写的程序可以:          轻松地本地化或翻译成不同的 ...

  6. java web.xml配置详解(转)

    源出处:java web.xml配置详解 1.常规配置:每一个站的WEB-INF下都有一个web.xml的设定文件,它提供了我们站台的配置设定. web.xml定义: .站台的名称和说明 .针对环境参 ...

  7. 【转】Eclipse Java注释模板设置详解

    Eclipse Java注释模板设置详解   设置注释模板的入口: Window->Preference->Java->Code Style->Code Template 然后 ...

  8. java ssl https 连接详解 生成证书 tomcat keystone

    java ssl https 连接详解 生成证书 我们先来了解一下什么理HTTPS 1. HTTPS概念 1)简介 HTTPS(全称:Hypertext Transfer Protocol over ...

  9. Java并发关键字Volatile 详解

    Java并发关键字Volatile 详解 问题引出: 1.Volatile是什么? 2.Volatile有哪些特性? 3.Volatile每个特性的底层实现原理是什么? 相关内容补充: 缓存一致性协议 ...

随机推荐

  1. pthread_getspecific()--读线程私有数据|pthread_setspecific()--写线程私有数据

    原型: #include <pthread.h> void *pthread_getspecific(pthread_key_t key); int pthread_setspecific ...

  2. CANopenNode drvTemplate/CO_driver.h hacking

    /************************************************************************ * CANopenNode drvTemplate/ ...

  3. 修改dedecms 列表页上一页 下一页 方法!

    dedecms根目录下include文件夹下:arc.listview.class.php文件! 1.简单文字替换:如 上一页替换成上页,直接替换即可! 2.文字替换成图片:上一页替换成<img ...

  4. java中io的详解

    注:本文全篇转载于:http://blog.csdn.net/taxueyingmei/article/details/7697042,觉得讲的挺详细,就借过来看看,挺不错的文章. 先贴一张图 Jav ...

  5. SPI驱动框架-1(DM8127 Linux2.6.37为例)

    一.驱动程序结构 1.platform_device 文件:/arch/arm/mach-omap2/device.c static struct omap2_mcspi_platform_confi ...

  6. Day2-Python基础2---列表、元组操作

    一.列表 列表是我们最以后最常用的数据类型之一,通过列表可以对数据实现最方便的存储.修改等操作 定义列表 names = ["maqing"," peilin" ...

  7. 杂项:MIME(多用途互联网邮件扩展类型)百科

    ylbtech-杂项:MIME(多用途互联网邮件扩展类型)百科 MIME(Multipurpose Internet Mail Extensions)多用途互联网邮件扩展类型.是设定某种扩展名的文件用 ...

  8. Oracle 常见进程

    1 服务器进程 专用服务器连接:数据连接跟服务器上的一个进程之间存在1:1的映射 共享服务器连接:多个会话共享一个服务器进程池,由一个调度程序分配 1.1 专用服务器连接 专用服务器连接模式下,客户连 ...

  9. jenkins学习 03 jenkins配置Maven项目

    我们的产品使用Git作为版本管理工具,而jenkins需要git插件来支持git,所以我们需要为jenkins添加git插件. 在Available tab页中找到Git Plugin 点击下方的In ...

  10. this、new、call和apply的相关问题

    讲解this指针的原理是个很复杂的问题,如果我们从javascript里this的实现机制来说明this,很多朋友可能会越来越糊涂,因此本篇打算换一个思路从应用的角度来讲解this指针,从这个角度理解 ...