java中文乱码问题详解

lhy0621 贡献于2014-01-20

作者 peaceyear  创建于2011-05-06 15:28:00   修改者jia  修改于2011-05-08 16:22:00字数13031

文档摘要: Abstract:本文深入分析了Java程序设计中Java编译器对java源文件和JVM对class类文件的编码/解码过程,通过此过程的解析透视出了Java编程中中文问题产生的根本原因,最后给出了建议的最优化的解决Java中文问题的方法。 
关键词:

java中文乱码问题详解 Abstract:本文深入分析了Java程序设计中Java编译器对java源文件和JVM对class类文件的编码/解码过程,通过此过程的解析透视出了Java编程中中文问题产生的根本原因,最后给出了建议的最优化的解决Java中文问题的方法。  1. 中文问题的来源     计算机最初的操作系统支持的编码是单字节的字符编码,于是,在计算机中一切处理程序最初都是以单字节编码的英文为准进行处理。随着计算机的发展,为了适应世界其它民族的语言(当然包括我们的汉字),人们提出了UNICODE编码,它采用双字节编码,兼容英文字符和其它民族的双字节字符编码,所以,目前,大多数国际性的软件内部均采用UNICODE编码,在软件运行时,它获得本地系统(多数时间是操作系统)默认支持的编码格式,然后再将软件内部的UNICODE转化为本地系统默认支持的格式显示出来。Java的JDK和JVM即是如此,我这里说的JDK是指国际版的JDK,我们大多数程序员使用的是国际化的JDK版本,以下所有的JDK均指国际化的JDK版本。我们的汉字是双字节编码语言,为了能让计算机处理中文,我们自己制定的gb2312、GBK、GBK2K等标准以适应计算机处理的需求。所以,大部分的操作系统为了适应我们处理中文的需求,均定制有中文操作系统,它们采用的是GBK,GB2312编码格式以正确显示我们的汉字。如:中文Win2K默认采用的是GBK编码显示,在中文WIN2k中保存文件时默认采用的保存文件的编码格式也是GBK的,即,所有在中文WIN2K中保存的文件它的内部编码默认均采用GBK编码,注意:GBK是在GB2312基础上扩充来的。     由于Java语言内部采用UNICODE编码,所以在JAVA程序运行时,就存在着一个从UNICODE编码和对应的操作系统及浏览器支持的编码格式转换输入、输出的问题,这个转换过程有着一系列的步骤,如果其中任何一步出错,则显示出来的汉字就会出是乱码,这就是我们常见的JAVA中文问题。     同时,Java是一个跨平台的编程语言,也即我们编写的程序不仅能在中文windows上运行,也能在中文Linux等系统上运行,同时也要求能在英文等系统上运行(我们经常看到有人把在中文win2k上编写的JAVA程序,移植到英文Linux上运行)。这种移植操作也会带来中文问题。     还有,有人使用英文的操作系统和英文的IE等浏览器,来运行带中文字符的程序和浏览中文网页,它们本身就不支持中文,也会带来中文问题。     几乎所有的浏览器默认在传递参数时都是以UTF-8编码格式来传递,而不是按中文编码传递,所以,传递中文参数时也会有问题,从而带来乱码现象。     总之,以上几个方面是JAVA中的中文问题的主要来源,我们把以上原因造成的程序不能正确运行而产生的问题称作:JAVA中文问题。 2. JAVA编码转换的详细过程     我们常见的JAVA程序包括以下类别:      *直接在console上运行的类(包括可视化界面的类)      *JSP代码类(注:JSP是Servlets类的变型)      *Servelets类      *EJB类      *其它不可以直接运行的支持类     这些类文件中,都有可能含有中文字符串,并且我们常用前三类JAVA程序和用户直接交互,用于输出和输入字符,如:我们在JSP和Servlet中得到客户端送来的字符,这些字符也包括中文字符。无论这些JAVA类的作用如何,这些JAVA程序的生命周期都是这样的: *编程人员在一定的操作系统上选择一个合适的编辑软件来实现源程序代码并以.java扩展名保存在操作系统中,例如我们在中文win2k中用记事本编辑一个java源程序;      *编程人员用JDK中的javac.exe来编译这些源代码,形成.class类(JSP文件是由容器调用JDK来编译的);      *直接运行这些类或将这些类布署到WEB容器中去运行,并输出结果。     那么,在这些过程中,JDK和JVM是如何将这些文件如何编码和解码并运行的呢? 这里,我们以中文win2k操作系统为例说明JAVA类是如何来编码和被解码的。     第一步,我们在中文win2k中用编辑软件如记事本编写一个Java源程序文件(包括以上五类JAVA程序),程序文件在保存时默认采用了操作系统默认支持GBK编码格式(操作系统默认支持的格式为file.encoding格式)形成了一个.java文件,也即,java程序在被编译前,我们的JAVA源程序文件是采用操作系统默认支持的file.encoding编码格式保存的,java源程序中含有中文信息字符和英文程序代码;要查看系统的file.encoding参数,可以用以下代码:   public class ShowSystemDefaultEncoding {   public static void main(String[] args) {   String encoding = System.getProperty("file.encoding");   System.out.println(encoding);   }}     第二步,我们用JDK的javac.exe文件编译我们的Java源程序,由于JDK是国际版的,在编译的时候,如果我们没有用-encoding参数指定我们的JAVA源程序的编码格式,则javac.exe首先获得我们操作系统默认采用的编码格式,也即在编译java程序时,若我们不指定源程序文件的编码格式,JDK首先获得操作系统的file.encoding参数(它保存的就是操作系统默认的编码格式,如WIN2k,它的值为GBK),然后JDK就把我们的java源程序从file.encoding编码格式转化为JAVA内部默认的UNICODE格式放入内存中。然后,javac把转换后的unicode格式的文件进行编译成.class类文件,此时.class文件是UNICODE编码的,它暂放在内存中,紧接着,JDK将此以UNICODE编码的编译后的class文件保存到我们的操作系统中形成我们见到的.class文件。对我们来说,我们最终获得的.class文件是内容以UNICODE编码格式保存的类文件,它内部包含我们源程序中的中文字符串,只不过此时它己经由file.encoding格式转化为UNICODE格式了。     这一步中,对于JSP源程序文件是不同的,对于JSP,这个过程是这样的:即WEB容器调用JSP编译器,JSP编译器先查看JSP文件中是否设置有文件编码格式,如果JSP文件中没有设置JSP文件的编码格式,则JSP编译器调用JDK先把JSP文件用JVM默认的字符编码格式(也即WEB容器所在的操作系统的默认的file.encoding)转化为临时的Servlet类,然后再把它编译成UNICODE格式的class类,并保存在临时文件夹中。如:在中文win2k上,WEB容器就把JSP文件从GBK编码格式转化为UNICODE格式,然后编译成临时保存的Servlet类,以响应用户的请求。     第三步,运行第二步编译出来的类,分为三种情况: A、 直接在console上运行的类     B、 EJB类和不可以直接运行的支持类(如JavaBean类)     C、 JSP代码和Servlet类     D、 JAVA程序和数据库之间     下面我们分这四种情况来看。     a) 直接在console上运行的类     这种情况,运行该类首先需要JVM支持,即操作系统中必须安装有JRE。运行过程是这样的:首先java启动JVM,此时JVM读出操作系统中保存的class文件并把内容读入内存中,此时内存中为UNICODE格式的class类,然后JVM运行它,如果此时此类需要接收用户输入,则类会默认用file.encoding编码格式对用户输入的串进行编码并转化为unicode保存入内存(用户可以设置输入流的编码格式)。程序运行后,产生的字符串(UNICODE编码的)再回交给JVM,最后JRE把此字符串再转化为file.encoding格式(用户可以设置输出流的编码格式)传递给操作系统显示接口并输出到界面上。     对于这种直接在console上运行的类,它的转化过程可用图1更加明确的表示出来: 图1 以上每一步的转化都需要正确的编码格式转化,才能最终不出现乱码现象。 b) EJB类和不可以直接运行的支持类(如JavaBean类)     由于EJB类和不可以直接运行的支持类,它们一般不与用户直接交互输入和输出,它们常常与其它的类进行交互输入和输出,所以它们在第二步被编译后,就形成了内容是UNICODE编码的类保存在操作系统中了,以后只要它与其它的类之间的交互在参数传递过程中没有丢失,则它就会正确的运行。 这种EJB类和不可以直接运行的支持类, 它的转化过程可用图2更加明确的表示出来: 图2 c) JSP代码和Servlet类     经过第二步后,JSP文件也被转化为Servlets类文件,只不过它不像标准的Servlets一校存在于classes目录中,它存在于WEB容器的临时目录中,故这一步中我们也把它做为Servlets来看。     对于Servlets,客户端请求它时,WEB容器调用它的JVM来运行Servlet,首先,JVM把Servlet的class类从系统中读出并装入内存中,内存中是以UNICODE编码的Servlet类的代码,然后JVM在内存中运行该Servlet类,如果Servlet在运行的过程中,需要接受从客户端传来的字符如:表单输入的值和URL中传入的值,此时如果程序中没有设定接受参数时采用的编码格式,则WEB容器会默认采用ISO-8859-1编码格式来接受传入的值并在JVM中转化为UNICODE格式的保存在WEB容器的内存中。Servlet运行后生成输出,输出的字符串是UNICODE格式的,紧接着,容器将Servlet运行产生的UNICODE格式的串(如html语法,用户输出的串等)直接发送到客户端浏览器上并输出给用户,如果此时指定了发送时输出的编码格式,则按指定的编码格式输出到浏览器上,如果没有指定,则默认按ISO-8859-1编码发送到客户的浏览器上。这种JSP代码和Servlet类,它的转化过程可用图3更加明确地表示出来: 图3 d) Java程序和数据库之间     对于几乎所有数据库的JDBC驱动程序,默认的在JAVA程序和数据库之间传递数据都是以ISO-8859-1为默认编码格式的,所以,我们的程序在向数据库内存储包含中文的数据时,JDBC首先是把程序内部的UNICODE编码格式的数据转化为ISO-8859-1的格式,然后传递到数据库中,在数据库保存数据时,它默认即以ISO-8859-1保存,所以,这是为什么我们常常在数据库中读出的中文数据是乱码。     对于JAVA程序和数据库之间的数据传递,我们可以用图4清晰地表示出来 图4 3. 分析常见的JAVA中文问题几个必须清楚的原则     首先,经过上面的详细分析,我们可以清晰地看到,任何JAVA程序的生命期中,其编码转换的关键过程是在于:最初编译成class文件的转码和最终向用户输出的转码过程。     其次,我们必须了解JAVA在编译时支持的、常用的编码格式有以下几种:     *ISO-8859-1,8-bit, 同8859_1,ISO-8859-1,ISO_8859_1等编码     *Cp1252,美国英语编码,同ANSI标准编码     *UTF-8,同unicode编码     *GB2312,同gb2312-80,gb2312-1980等编码     *GBK , 同MS936,它是gb2312的扩充     及其它的编码,如韩文、日文、繁体中文等。同时,我们要注意这些编码间的兼容关体系如下:     unicode和UTF-8编码是一一对应的关系。GB2312可以认为是GBK的子集,即GBK编码是在gb2312上扩展来的。同时,GBK编码包含了20902个汉字,编码范围为:0x8140-0xfefe,所有的字符可以一一对应到UNICODE2.0中来。     再次,对于放在操作系统中的.java源程序文件,在编译时,我们可以指定它内容的编码格式,具体来说用-encoding来指定。注意:如果源程序中含有中文字符,而你用-encoding指定为其它的编码字符,显然是要出错的。用-encoding指定源文件的编码方式为GBK或gb2312,无论我们在什么系统上编译含有中文字符的JAVA源程序都不会有问题,它都会正确地将中文转化为UNICODE存储在class文件中。          然后,我们必须清楚,几乎所有的WEB容器在其内部默认的字符编码格式都是以ISO-8859-1为默认值的,同时,几乎所有的浏览器在传递参数时都是默认以UTF-8的方式来传递参数的。所以,虽然我们的Java源文件在出入口的地方指定了正确的编码方式,但其在容器内部运行时还是以ISO-8859-1来处理的。 4. 中文问题的分类及其建议最优解决办法     了解以上JAVA处理文件的原理之后,我们就可以提出了一套建议最优的解决汉字问题的办法。     我们的目标是:我们在中文系统中编辑的含有中文字符串或进行中文处理的JAVA源程序经编译后可以移值到任何其它的操作系统中正确运行,或拿到其它操作系统中编译后能正确运行,能正确地传递中文和英文参数,能正确地和数据库交流中英文字符串。     我们的具体思路是:在JAVA程序转码的入口和出口及JAVA程序同用户有输入输出转换的地方限制编码方法使之正确即可。     具体解决办法如下: 1) 针对直接在console上运行的类     对于这种情况,我们建议在程序编写时,如果需要从用户端接收用户的可能含有中文的输入或含有中文的输出,程序中应该采用字符流来处理输入和输出,具体来说,应用以下面向字符型节点流类型:     对文件:FileReader,FileWrieter         其字节型节点流类型为:FileInputStream,FileOutputStream     对内存(数组):CharArrayReader,CharArrayWriter         其字节型节点流类型为:ByteArrayInputStream,ByteArrayOutputStream     对内存(字符串):StringReader,StringWriter     对管道:PipedReader,PipedWriter         其字节型节点流类型为:PipedInputStream,PipedOutputStream     同时,应该用以下面向字符型处理流来处理输入和输出:     BufferedWriter,BufferedReader         其字节型的处理流为:BufferedInputeStream,BufferedOutputStream     InputStreamReader,OutputStreamWriter     其字节型的处理流为:DataInputStream,DataOutputStream     其中InputStreamReader和InputStreamWriter用于将字节流按照指定的字符编码集转换到字符流,如:     InputStreamReader in = new InputStreamReader(System.in,"GB2312");     OutputStreamWriter out = new OutputStreamWriter (System.out,"GB2312");     例如:采用如下的示例JAVA编码就达到了要求:     //Read.java     import java.io.*;     public class Read {     public static void main(String[] args) throws IOException {     String str = "\n中文测试,这是内部硬编码的串"+"\ntest english character";     String strin= "";     BufferedReader stdin = new BufferedReader(new InputStreamReader(System.in,"gb2312")); //设置输入接口按中文编码     BufferedWriter stdout = new BufferedWriter(new OutputStreamWriter(System.out,"gb2312")); //设置输出接口按中文编码     stdout.write("请输入:");     stdout.flush();     strin = stdin.readLine();     stdout.write("这是从用户输入的串:"+strin);     stdout.write(str);     stdout.flush();     }}     同时,在编译程序时,我们用以下方式来进行:     javac -encoding gb2312 Read.java     其运行结果如图5所示: 图5 2) 针对EJB类和不可以直接运行的支持类(如JavaBean类)     由于这种类它们本身被其它的类调用,不直接与用户交互,故对这种类来说,我们的建议的处理方式是内部程序中应该采用字符流来处理程序内部的中文字符串(具体如上面一节中一样),同时,在编译类时用-encoding gb2312参数指示源文件是中文格式编码的即可。 3) 针对Servlet类     针对Servlet,我们建议用以下方法:     在编译Servlet类的源程序时,用-encoding指定编码为GBK或GB2312,且在向用户输出时的编码部分用response对象的setContentType("text/html;charset=GBK");或gb2312来设置输出编码格式,同样在接收用户输入时,我们用request.setCharacterEncoding("GB2312");这样无论我们的servlet类移植到什么操作系统中,只有客户端的浏览器支持中文显示,就可以正确显示。如下是一个正确的示例:     //HelloWorld.java     package hello;     import java.io.*;     import javax.servlet.*;     import javax.servlet.http.*;     public class HelloWorld extends HttpServlet     {     public void init() throws ServletException { }     public void doGet(HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException     {     request.setCharacterEncoding("GB2312"); //设置输入编码格式     response.setContentType("text/html;charset=GB2312"); //设置输出编码格式     PrintWriter out = response.getWriter(); //建议使用PrintWriter输出     out.println("
");     out.println("Hello World! This is created by Servlet!测试中文!");     out.println("
");     }     public void doPost(HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException     {     request.setCharacterEncoding("GB2312"); //设置输入编码格式     response.setContentType("text/html;charset=GB2312"); //设置输出编码格式     String name = request.getParameter("name");     String id = request.getParameter("id");     if(name==null) name="";     if(id==null) id="";     PrintWriter out = response.getWriter(); //建议使用PrintWriter输出     out.println("
");     out.println("你传入的中文字串是:" + name);     out.println("
你输入的id是:" + id);     out.println("
");     }     public void destroy() { }     }         请用javac -encoding gb2312 HelloWorld.java来编译此程序。         测试此Servlet的程序如下所示:     <%@page contentType="text/html; charset=gb2312"%>     <%request.setCharacterEncoding("GB2312");%>                
        传给Servlet    
    其运行结果如图6所示: 图6 4) JAVA程序和数据库之间     为避免JAVA程序和数据库之间数据传递出现乱码现象,我们建议采用以下最优方法来处理:     1、 对于JAVA程序的处理方法按我们指定的方法处理。     2、 把数据库默认支持的编码格式改为GBK或GB2312的。     如:在mysql中,我们可以在配置文件my.ini中加入以下语句实现:     在[mysqld]区增加:     default-character-set=gbk     并增加:     [client]     default-character-set=gbk     在SQL Server2K中,我们可以将数据库默认的语言设置为Simplified Chinese来达到目的。 5) 针对JSP代码     由于JSP是在运行时,由WEB容器进行动态编译的,如果我们没有指定JSP源文件的编码格式,则JSP编译器会获得服务器操作系统的file.encoding值来对JSP文件编译的,它在移植时最容易出问题,如在中文win2k中可以很好运行的jsp文件拿到英文linux中就不行,尽管客户端都是一样的,那是因为容器在编译JSP文件时获取的操作系统的编码不同造成的(在中文wink中的file.encoding和在英文Linux中file.encoding是不同的,且英文Linux的file.encoding对中文不支持,所以编译出来的JSP类就会有问题)。 网络上讨论的大多数是此类问题,多是因为JSP文件移植平台时不能正确显示的问题,对于这类问题,我们了解了JAVA中程序编码转换的原理,解决起来就容易多了。我们建议的解决办法如下:     1、我们要保证JSP向客户端输出时是采用中文编码方式输出的,即无论如何我们首先在我们的JSP源代编中加入以下一行:     <%@page contentType="text/html; charset=gb2312"%>     2、为了让JSP能正确获得传入的参数,我们在JSP源文件头加入下面一句:     <%request.setCharacterEncoding("GB2312");%>     3、为了让JSP编译器能正确地解码我们的含有中文字符的JSP文件,我们需要在JSP源文件中指定我们的JSP源文件的编码格式,具体来说,我们在JSP源文件头上加入下面的一句即可:     <%@page pageEncoding="GB2312"%>或<%@page pageEncoding="GBK"%>     这是JSP规范2.0新增加的指令。     我们建议使用此方法来解JSP文件中的中文问题,下面的代码是一个正确做法的JSP文件的测试程序: //testchinese.jsp     <%@page pageEncoding="GB2312"%>     <%@page contentType="text/html; charset=gb2312"%>     <%request.setCharacterEncoding("GB2312");%>     <%     String action = request.getParameter("ACTION");     String name = "";     String str = "";     if(action!=null && action.equals("SENT"))     {     name = request.getParameter("name");     str = request.getParameter("str");     }     %>                            
        提交    
    <%     if(action!=null && action.equals("SENT"))     {     out.println("
你输入的字符为:"+name);     out.println("
你通过URL传入的字符为:"+str);     }     %>             如图7是此程序运行的结果示意图:     图7 5. 总结     在上面的详细分析中,我们清晰地给出了JAVA在处理源程序过程中的详细转换过程,为我们正确解决JAVA编程中的中文问题提供了基础。同时,我们给出了认为是最优的解决JAVA中文问题的办法。 Java中文问题一直困扰着很多初学者,如果了解了Java系统的中文问题原理,我们就可以对中文问题能够采取根本的解决之道。   最古老的解决方案是使用String的字节码转换,这种方案问题是不方便,我们需要破坏对象封装性,进行字节码转换。   还有一种方式是对J2EE容器进行编码设置,如果J2EE应用系统脱离该容器,则会发生乱码,而且指定容器配置不符合J2EE应用和容器分离的原则。   在Java内部运算中,涉及到的所有字符串都会被转化为UTF-8编码来进行运算。那么,在被Java转化之前,字符串是什么样的字符集? Java总是根据操作系统的默认编码字符集来决定字符串的初始编码,而且Java系统的输入和输出的都是采取操作系统的默认编码。   因此,如果能统一Java系统的输入、输出和操作系统3者的编码字符集合,将能够使Java系统正确处理和显示汉字。这是处理Java系统汉字的一个原则,但是在实际项目中,能够正确抓住和控制住Java系统的输入和输出部分是比较难的。J2EE中,由于涉及到外部浏览器和数据库等,所以中文问题乱码显得非常突出。   J2EE应用程序是运行在J2EE容器中。在这个系统中,输入途径有很多种:一种是通过页面表单打包成请求(request)发往服务器的;第二种是通过数据库读入;还有第3种输入比较复杂,JSP在第一次运行时总是被编译成Servlet,JSP中常常包含中文字符,那么编译使用javac时,Java将根据默认的操作系统编码作为初始编码。除非特别指定,如在Jbuilder/eclipse中可以指定默认的字符集。   输出途径也有几种:第一种是JSP页面的输出。由于JSP页面已经被编译成Servlet,那么在输出时,也将根据操作系统的默认编码来选择输出编码,除非指定输出编码方式;还有输出途径是数据库,将字符串输出到数据库。   由此看来,一个J2EE系统的输入输出是非常复杂,而且是动态变化的,而Java是跨平台运行的,在实际编译和运行中,都可能涉及到不同的操作系统,如果任由Java自由根据操作系统来决定输入输出的编码字符集,这将不可控制地出现乱码。   正是由于Java的跨平台特性,使得字符集问题必须由具体系统来统一解决,所以在一个Java应用系统中,解决中文乱码的根本办法是明确指定整个应用系统统一字符集。   指定统一字符集时,到底是指定ISO8859_1 、GBK还是UTF-8呢?   (1)如统一指定为ISO8859_1,因为目前大多数软件都是西方人编制的,他们默认的字符集就是ISO8859_1,包括操作系统Linux和数据库MySQL等。这样,如果指定Jive统一编码为ISO8859_1,那么就有下面3个环节必须把握:   开发和编译代码时指定字符集为ISO8859_1。   运行操作系统的默认编码必须是ISO8859_1,如Linux。   在JSP头部声明:<%@ page c %>。   (2)如果统一指定为GBK中文字符集,上述3个环节同样需要做到,不同的是只能运行在默认编码为GBK的操作系统,如中文Windows。   统一编码为ISO8859_1和GBK虽然带来编制代码的方便,但是各自只能在相应的操作系统上运行。但是也破坏了Java跨平台运行的优越性,只在一定范围内行得通。例如,为了使得GBK编码在linux上运行,设置Linux编码为GBK。   那么有没有一种除了应用系统以外不需要进行任何附加设置的中文编码根本解决方案呢?   将Java/J2EE系统的统一编码定义为UTF-8。UTF-8编码是一种兼容所有语言的编码方式,惟一比较麻烦的就是要找到应用系统的所有出入口,然后使用UTF-8去“结扎”它。   一个J2EE应用系统需要做下列几步工作: 1. 开发和编译代码时指定字符集为UTF-8。JBuilder和Eclipse都可以在项目属性中设置。 2. 使用过滤器,如果所有请求都经过一个Servlet控制分配器,那么使用Servlet的filter执行语句,将所有来自浏览器的请求(request)转换为UTF-8,因为浏览器发过来的请求包根据浏览器所在的操作系统编码,可能是各种形式编码。关键一句: request.setCharacterEncoding("UTF-8")。 网上有此filter的源码,Jdon框架源码中com.jdon.util.SetCharacterEncodingFilter 需要配置web.xml 激活该Filter。 3. 在JSP头部声明:<%@ page c %>。 4. 在Jsp的html代码中,声明UTF-8: 5. 设定数据库连接方式是UTF-8。例如连接MYSQL时配置URL如下: jdbc:mysql://localhost:3306/test?useUnicode=true&characterEncoding=UTF-8 注意,上述写法是JBoss的mysql-ds.xml写法,多亏网友提示,在tomcat中&要写成&即可。一般其他数据库都可以通过管理设置设定UTF-8 6. 其他和外界交互时能够设定编码时就设定UTF-8,例如读取文件,操作XML等。      笔者以前在Jsp/Servlet时就采取这个原则,后来使用Struts、Tapestry、EJB、Hibernate、Jdon等框架时,从未被乱码困扰过,可以说适合各种架构。希望本方案供更多初学者分享,减少Java/J2EE的第一个拦路虎,也避免因为采取一些临时解决方案,导致中文问题一直出现在新的技术架构中。

下载文档到电脑,查找使用更方便

文档的实际排版效果,会与网站的显示效果略有不同!!

需要 6 金币 [ 分享文档获得金币 ] 0 人已下载

下载文档