URLEncoder和URLDecoder(乱码处理)
前言
在進(jìn)行向服務(wù)器傳遞表單數(shù)據(jù)的實(shí)驗(yàn)的時(shí)候,發(fā)現(xiàn)得到的英文字符正常而中文字符都是亂碼。在百思不得其解的時(shí)候,學(xué)習(xí)了一下URLEncoder和URLDecoder,以及順藤摸瓜找到了產(chǎn)生亂碼的原因和解決辦法,在此記錄一波。
URLEncoder和URLDecoder
URLEncoder和URLDecoder主要用完成普通字符和application/x-www-form-urlencodedMIME字符串之間的相互轉(zhuǎn)換,是HTML格式編碼的實(shí)用工具類。
轉(zhuǎn)換規(guī)則:
- 字母數(shù)字字符 “a” 到 “z”、“A” 到 “Z” 和 “0” 到 “9” 保持不變。
- .特殊字符 “.”、"-"、"*" 和 “_” 保持不變。
- 空格字符 " " 轉(zhuǎn)換為一個(gè)加號 “+”。
- 所有其他字符都是不安全的,因此首先使用一些編碼機(jī)制將它們轉(zhuǎn)換為一個(gè)或多個(gè)字節(jié)。然后每個(gè)字節(jié)用一個(gè)包含 3 個(gè)字符的字符串 “%xy” 表示,其中 xy 為該字節(jié)的兩位十六進(jìn)制表示形式。推薦的編碼機(jī)制是 UTF-8。但是,出于兼容性考慮,如果未指定一種編碼,則使用相應(yīng)平臺的默認(rèn)編碼。
示例代碼
try {String url = "測試中文串";System.out.println(url);//通過utf-8編碼把中文字符串轉(zhuǎn)化為application/x-www-form-urlencodedMIME字符串String encodeUrl = URLEncoder.encode(url, "utf-8");System.out.println(encodeUrl);//同樣通過utf-8編碼把a(bǔ)pplication/x-www-form-urlencodedMIME字符串解碼為原來的字符串String decodeUrl = URLDecoder.decode(encodeUrl, "utf-8");System.out.println(decodeUrl); } catch (Exception e) {e.printStackTrace(); }結(jié)果輸出
測試中文串 %E6%B5%8B%E8%AF%95%E4%B8%AD%E6%96%87%E4%B8%B2 測試中文串亂碼產(chǎn)生原因以及解決
亂碼產(chǎn)生原因:服務(wù)器端在調(diào)用request.getParameter(parameterName)獲取參數(shù)之前會(huì)自動(dòng)通過"ISO8859-1"編碼對參數(shù)進(jìn)行了一次解碼操作,相當(dāng)于調(diào)用了一次 URLDecoder.decode(parameterValue, “ISO8859-1”)。在我們獲取到參數(shù)之后,又對獲取到的參數(shù)進(jìn)行了一次解碼,于是出現(xiàn)了亂碼現(xiàn)象。相對于:
try {String url = "測試中文串";System.out.println(url);//經(jīng)過編碼后得到application/x-www-form-urlencodedMIM*字符串String encodeUrl = URLEncoder.encode(url, "utf-8");System.out.println(encodeUrl);//服務(wù)器端自動(dòng)進(jìn)行的解碼操作encodeUrl = URLDecoder.decode(encodeUrl, "ISO8859-1"); System.out.println(encodeUrl);//我們獲取到參數(shù)的時(shí)候進(jìn)行的操作String decodeUrl = URLDecoder.decode(encodeUrl, "utf-8");System.out.println(decodeUrl); } catch (Exception e) {e.printStackTrace(); }于是我們得到帶有亂碼的結(jié)果:
測試中文串 %E6%B5%8B%E8%AF%95%E4%B8%AD%E6%96%87%E4%B8%B2 ???è??????????? ???è???????????針對這種現(xiàn)象,這里提供了兩種解決方法:
方法一:利用String的構(gòu)造函數(shù)進(jìn)行轉(zhuǎn)碼(常用,推薦)
解決效果演示:
try {String url = "測試中文串";System.out.println(url);String encodeUrl = URLEncoder.encode(url, "utf-8");System.out.println(encodeUrl);//服務(wù)器端自動(dòng)進(jìn)行的解碼操作encodeUrl = URLDecoder.decode(encodeUrl, "ISO8859-1"); System.out.println(encodeUrl);//轉(zhuǎn)碼操作String decodeUrl = new String(encodeUrl.getBytes("ISO8859-1"), "utf-8");System.out.println(decodeUrl); } catch (Exception e) {e.printStackTrace(); }運(yùn)行效果:
測試中文串 %E6%B5%8B%E8%AF%95%E4%B8%AD%E6%96%87%E4%B8%B2 ???è??????????? 測試中文串方法二:開始時(shí)對中文參數(shù)進(jìn)行兩次”utf-8“編碼
這個(gè)方法同樣可以解決這個(gè)問題,由上文給出的規(guī)則可以知道,第二次編碼是對第一次編碼的到的串中的’%'進(jìn)行編碼,雖然解碼的時(shí)候使用的是ISO-8859-1,但是對于%和字母數(shù)字而言用ISO-8859-1和UTF-8解碼出來的是一樣的,這樣經(jīng)過服務(wù)器的自動(dòng)解碼就可以得到第一次編碼得到的串。當(dāng)我們獲取到參數(shù)再次用"utf-8"解碼的時(shí)候,就可以得到原來的中文字符串了。
//此部分不作演示
參考資料
總結(jié)
以上是生活随笔為你收集整理的URLEncoder和URLDecoder(乱码处理)的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: UVA-11995(STL+模拟)附讲解
- 下一篇: spring boot参数为日期的查询