看了一下几位的文章:
http://blog.csdn.net/Breeze2003/archive/2008/11/25/3368406.aspx
这位写的很好,介绍了编码与解码的关系
http://blog.csdn.net/yzhz/archive/2007/07/03/1676796.aspx
http://blog.csdn.net/sfdev/archive/2009/01/20/3841719.aspx
这2为介绍的比较全面
http://www.javaeye.com/topic/398782
http://www.javaeye.com/topic/97803
这里介绍了字符集和编码的基本常识
我做个总结好了,我文采不太好。。。
交代下我的环境,tomcat用的默认编码iso-8859-1,jsp页面用的gb2312,filter过滤器用的gb2312,这样表单post过来的没问题。
首先介绍下字节与字符。
字节:计算机中存储数据的单元,一个8位的二进制数,是一个很具体的存储空间。
字符:人们使用的记号,抽象意义上的一个符号,肯能对应多个字节。在Java中,字符串用统一的Unicode编码,每个字符占用两个字节,某种意义上/uxxxx就代表一个字符。
上面几位那转过来的,在这里标明下。
HttpServletRequest.getParameter("name"); //返回的字符串为:queryString(包括get和post),其值经过Servlet服务器URL Decode(解码)过的,默认编码来源于应用服务器中的配置,比如tomcat中server.xml的URIEncoding。
HttpServletRequest.getPathInfo(); //同上
HttpServletRequest.getRequestURI(); //返回的字符串为:contextPath/servletPath/pathinfo;注意是浏览器提交过来的原始数据,未被Servlet服务器URL Decode过。
1、函数介绍
1)将字符串用指定的编码集合解析成字节数组,完成Unicode-〉charsetName转换
public byte[] getBytes(String charsetName) throws UnsupportedEncodingException
2)将字节数组以指定的编码集合构造成字符串,完成charsetName-〉Unicode转换
public String(byte[] bytes, String charsetName) throws UnsupportedEncodingException。
网页表单提交时候的编码:
当网页上的表单(form)提交数据到 Web 服务器时,'?', '&', '=', '%', '+' 等符号在提交的数据中都有特殊的定义和用途。因此,如果所要提交的某个表单项中,包含这些符号,那么这些符号就需要进行一下转化,然后服务器再进行逆向转 化而得到本来所要提交的数据。
转化的格式是:%XX (百分号再跟上被转化符号的16进制编码,根据特定的编码规则得到16进制数,比如utf-8,bg2312等)。url中pathinfo与queryString部分也是这样。
看url传递参数和表单get的情况,表单会更具jsp的contentType中指定的字符集编码,我的是gb2312,而url会根据ie的默认字符集来编码,也就是GBK。传到服务器以后,tomcat会根据默认字符集iso-8859-1来解码(我认为是用了函数2,服务器将ie传过来的字节码解码了),我们用request.getParameter("name");就会得到乱码,所以我们要先用 public byte[] getBytes(String charsetName) 重新得到原始的字节码,在用public String(byte[] bytes, String charsetName)得到正确的字符串。
对于POST方式,表单中的参数值对是通过request body发送给服务器,此时浏览器会根据网页的ContentType("text/html; charset=GBK")中指定的编码进行对表单中的数据进行编码,然后发给服务器。
在服务器端的程序中我们可以通过Request.setCharacterEncoding() 设置编码,然后通过request.getParameter获得正确的数据。
不知道这里是否经过了服务器解码,解码是在什么时候做的,还是有点不明白?
下面说下关于AJAX传递中文参数,我们利用 XMLHttpRequest对象传递的中文参数。
我做了个实验利用了javascript的encodeURI()函数对url进行编码,它用的是utf-8。
首先用window.location.href=encodeURI(url);
在服务器用request.getParameter("name")会得到????,证明他经过了iso-8859-1的编码,用URLDecoder.decode()方法解码无法得到正确的结果,用new String(bytes,"utf-8")可以得到正确结果。这种情况下用Js函数好像没什么用
其次利用$.ajax()方式,我用的jquery框架,传递过来的参数,用request.getParameter("name")得到了url编码后的,也就是%xx%xx%xx,用URLDecoder.decode()方法解码可以得到正确结果,好像没有经过服务器解码,原来$.ajax()默认是用get方式,当传递data参数时变为post方式,所以他未经过服务器解码的,但好像也没经过filter解码。。。