js编码处理

1.使用JS中的encodeURIComponent或encodeURI方法。

说明:

encodeURIComponent(String)

对传递参数进行设置。不编码字符有71个:!,',(,),*,-,.,_,~,0-9,a-z,A-Z。

例:

var url = “中国”;

encodeURI(String)

对URL整体转换。不编码字符有82个:!,#,$,&,',(,),*,+,,,-,.,/,:,;,=,?,@,_,~,0-9,a-z,A-Z。

例:

var url = “中国”;

乱码处理实例:

/////////////////////////////////////////////////////////////////////////////////////

初始页面内容如下(hello.jsp):

/////////////////////////////////////////////////////////////////////////////////////

<%@ page language="java" import="java.util.*" pageEncoding="GB18030"%>

<%String path = request.getContextPath();%>

AJAX提交页面

function justdo(){

var post="name=王力猛&email=wallimn@sohu.com&bokee=http://wallimn.bokee.com";

post = encodeURI(post);

post = encodeURI(post);//两次,很关键var xmlObj = new ActiveXObject('Msxml2.XMLHTTP');

var URL = '<%= path%>/page/act.jsp';//文件名需要调整成测试时的相应位置?

xmlObj.open ('post',URL,true);

xmlObj.setrequestheader("cache-control","no-cache");

xmlObj.setrequestheader("Content-Type","application/x-www-form-urlencoded");

xmlObj.send (post);//注意:POST方式,使用这个来发送内容?

}

/////////////////////////////////////////////////////////////////////////////////////

ajax请求处理页面(act.jsp)的内容如下:

/////////////////////////////////////////////////////////////////////////////////////

<%@ page language="java" import="java.util.*" pageEncoding="GB18030"%>

<%String path = request.getContextPath();%>

<

%@pageimport="java.net.URLDecoder"%>

ajax deal

<%

//遍历输出参数内容。

for (Enumeration e = request.getParameterNames(); e.hasMoreElements();) {

String h = (String) e.nextElement();

String v = request.getParameter(h);

String mm =   java.net.URLDecoder.decode(v

,"UTF-8");

System.out.println("请求参数: " + h + " = " + mm);

}

%>

/////////////////////////////////////////////////////////////////////////////////////

说明:

java.net.URLencode和java.net.URLDecode分别对应于JavaScript中的encodeURI和decodeURI、encodeURIComponent和decodeURIComponent.

为什么要连续两次调用encodeURI(String)方法呢?是因为Java中的request.getParameter(String)方法会进行一次URI的解码过程,调用时内置的解码过程会导致乱码出现。而URI编码两次后,request.getParameter(String)函数得到的是原信息URI编码一次的内容。接着用java.net.URLDecoder.decode(String str,String codename)方法,将已经编码的URI转换成原文。

2.使用JS中的escape方法。

说明:

escape(String)

对0-255以外的unicode值进行编码时输出%u****格式,其它情况下escape,encodeURI,encodeURIComponent编码结果相同。

例:

var url = “中国”;

乱码处理实例:

/////////////////////////////////////////////////////////////////////////////////////

例子跟上面一样。只有这里不同。

(hello.jsp)

post = escape(post);

post = escape (post);//两次,很关键

(act.jsp)

String h = (String) e.nextElement();

String v = request.getParameter(h);

String mm =EscapeUnescape.unescape(v,"UTF-8");

System.out.println("请求参数: " + h + " = " + mm);

/////////////////////////////////////////////////////////////////////////////////////

(EscapeUnescape.java)Java中的escape和unescape.内容如下:

/////////////////////////////////////////////////////////////////////////////////////

package cn.kgnews.util;

public classEscapeUnescape{

public static String escape(String src) {

int i;

char j;

StringBuffer tmp = new StringBuffer();

tmp.ensureCapacity(src.length() * 6);

for (i = 0; i < src.length(); i++) {

j = src.charAt(i);

if (Character.isDigit(j) || Character.isLowerCase(j)

|| Character.isUpperCase(j))

tmp.append(j);

else if (j < 256) {

tmp.append("%");

if (j < 16)

tmp.append("0");

tmp.append(Integer.toString(j,16));

} else {

tmp.append("%u");

tmp.append(Integer.toString(j,16));

}

}

return tmp.toString();

}

public static String unescape(String src) {

StringBuffer tmp = new StringBuffer();

tmp.ensureCapacity(src.length());

int lastPos = 0,pos = 0;

char ch;

while (lastPos < src.length()) {

pos = src.indexOf("%",lastPos);

if (pos == lastPos) {

if (src.charAt(pos + 1) == 'u') {

ch = (char) Integer.parseInt(src

.substring(pos + 2,pos + 6),16);

tmp.append(ch);

lastPos = pos + 6;

} else {

ch = (char) Integer.parseInt(src

.substring(pos + 1,pos + 3),16);

tmp.append(ch);

lastPos = pos + 3;

}

} else {

if (pos == -1) {

tmp.append(src.substring(lastPos));

lastPos = src.length();

} else {

tmp.append(src.substring(lastPos,pos));

lastPos = pos;

}

}

}

return tmp.toString();

}

}

/////////////////////////////////////////////////////////////////////////////////////

说明:

EscapeUnescape.java类是Java中的escape和unescape。

原理跟上例一样。

3.用JavaScript实现java中的URLencode跟URLdecode.

说明:

这种方法服务器端代码不必修改。直接request.getParameter()来获取就可以了。

JavaScript中的URLencode跟URLdecode实现如下:

/////////////////////////////////////////////////////////////////////////////////////

(UrlEncodeUrlDecode_gecko.js)非IE实现方法如下:

完整代码可到这里下载:

http://www.blueidea.com/user/qswh/qswhU2GB.js

/////////////////////////////////////////////////////////////////////////////////////

var qswhU2GB = […..]; //此数组为GB Unicode对照表

function UrlEncode(str){

var i,c,ret="",strSpecial="!\"#$%&'()*+,/:;<=>?@[\]^`{|}~%";

for(i=0;i

if(str.charCodeAt(i)>=0x4e00){

c=qswhU2GB[str.charCodeAt(i)-0x4e00];

ret+="%"+c.slice(0,2)+"%"+c.slice(-2);

}

else{

c=str.charAt(i);

if(c==" ")

ret+="+";

else if(strSpecial.indexOf(c)!=-1)

ret+="%"+str.charCodeAt(i).toString(16);

else

ret+=c;

}

}

return ret;

}

function UrlDecode(str){

var i,c,d,t,p,ret = "";

function findPos(str){

for(var j = 0; j < qswhU2GB.length; j++){

if(qswhU2GB[j] == str){

return j;

}

}

return -1;

}

for(i = 0;i < str.length;){

c = str.charAt(i);i++;

if(c != "%"){

if(c == "+"){

ret += " ";

}else{

ret += c;

}

}else{

t = str.substring(i,i+2);i += 2;

if(("0x" + t) > 0xA0){

d = str.substring(i+1,i+3);i += 3;

p = findPos(t + d);

if(p != -1){

ret += String.fromCharCode(p + 0x4e00);

}

}else{

ret += String.fromCharCode("0x" + t);

}

}

}

return ret;

}

function getSpell(str,sp){

var i,c,t,ret="";

if(sp==null)sp="";

for(i=0;i

if(str.charCodeAt(i)>=0x4e00){

c=parseInt(qswhU2GB[str.charCodeAt(i)-0x4e00],16);

if(c<55290){

for(t=qswhSpell.length-1;t>0;t=t-2)if(qswhSpell[t]<=c)break;

if(t>0)ret+=qswhSpell[t-1]+sp;

}

}

}

return ret.substr(0,ret.length-sp.length);

}

/////////////////////////////////////////////////////////////////////////////////////

(UrlEncodeUrlDecode_ie.js)IE实现方法如下:

/////////////////////////////////////////////////////////////////////////////////////

function UrlEncode(str) {

var ret = "";

var strSpecial = " ~!\"#$%&'()*+-,/:;<=>?[]^`{|}~%";

for (var i = 0; i < str.length; i++) {

var chr = str.charAt(i);

strstr = chr;

execScript("c = hex(asc(strstr))","VBScript");

if (parseInt("0x" + c) > 127) {

ret += "%" + c.slice(0,2) + "%" + c.slice(-2);

} else {

if (strSpecial.indexOf(chr) != -1) {

ret += "%" + c.toString(16);

} else {

ret += chr;

}

}

}

return ret;

}

function UrlDecode(str) {

var ret = "";

for (var i = 0; i < str.length; i++) {

var chr = str.charAt(i);

if (chr == "+") {

ret += " ";

} else {

if (chr == "%") {

var asc = str.substring(i + 1,i + 3);

if (parseInt("0x" + asc) > 127) {

temp = parseInt("0x" + asc + str.substring(i + 4,i + 6));

execScript("rt = chr(temp)","VBScript");

ret += rt;

i += 5;

} else {

temp = parseInt("0x" + asc);

execScript("ret = ret + chr(temp)","VBScript");

i += 2;

}

} else {

ret += chr;

}

}

}

return ret;

}

/////////////////////////////////////////////////////////////////////////////////////

(loadcssorjs.js)自动识别浏览器动态导入JS/CSS

实现方法如下:

/////////////////////////////////////////////////////////////////////////////////////

/*

CopyRight(C)CAnca Software Office.

Created by CAnca.2007.9.4

*/

function LoadScript(url) {

document.write("");

}

function LoadCss(url) {

document.write("");

}

var sSuffix = /msie/.test(navigator.userAgent.toLowerCase()) ? "ie" : "gecko";

LoadScript("js/UrlEncodeUrlDecode_" + sSuffix + ".js");

使用方法:

将三个JS文件放在同目录。在页面导入loadcssorjs.js。在要进行编码的地方使用UrlEncode方法即可。

例:

//index.html

var url = “http://cancait.blog.163.com/name=” +UrlEncode(“中国人”);

window.open(url);

…..

三种解决方案的比较:

第一种,在服务器端需要一次java.net.URLdecode(String)转码。使用起来,不太方便。

第二种,要建立Java版的escape跟uncape。在服务器端还是需要一次uncape转码。使用起来,不太方便。

第三种,是最方便的一种方法。只需要客户端进行编码。服务器端可以不做任何修改。唯一缺点的是:firefox浏览网页时,要加载一个150K的UrlEncodeUrlDecode_gecko.js文件。影响了浏览速度。(但本人还是推荐使用这方案。)

总结:

当然,Ajax实现不乱码,可以不用这三种方案,用这三种方案,只是迫不得已的做法。通常造成乱码的原因有以下几点:

1.xmlhttp返回的数据默认的字符编码是utf-8,如果前台页面是gb2312或者其它编码数据就会产生乱码。

2.post方法提交数据默认的字符编码是utf-8,如果后台是gb2312或其他编码数据就会产生乱码。

解决方法:

推荐方法:由于Javascript沿用java的字符处理方式,内部是使用unicode来处理所有字符的。前台后台都用utf-8编码,这样可以省不少麻烦,从根本上解决了乱码问题.优点是效率高,而且符合目前的形式,utf-8编码本身就是一种比较优秀的编码,没有语言限制.缺点只能调用自己的后台编码或者其他的utf-8的编码。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 199,440评论 5 467
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 83,814评论 2 376
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 146,427评论 0 330
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 53,710评论 1 270
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 62,625评论 5 359
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,014评论 1 275
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,511评论 3 390
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,162评论 0 254
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,311评论 1 294
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,262评论 2 317
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,278评论 1 328
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 32,989评论 3 316
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,583评论 3 303
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,664评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 30,904评论 1 255
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 42,274评论 2 345
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 41,856评论 2 339

推荐阅读更多精彩内容

  • 一. Java基础部分.................................................
    wy_sure阅读 3,780评论 0 11
  • 1. Java基础部分 基础部分的顺序:基本语法,类相关的语法,内部类的语法,继承相关的语法,异常的语法,线程的语...
    子非鱼_t_阅读 31,531评论 18 399
  • 单例模式 适用场景:可能会在场景中使用到对象,但只有一个实例,加载时并不主动创建,需要时才创建 最常见的单例模式,...
    Obeing阅读 2,046评论 1 10
  • 个人学习批处理的初衷来源于实际工作;在某个迭代版本有个BS(安卓手游模拟器)大需求,从而在测试过程中就重复涉及到...
    Luckykailiu阅读 4,670评论 0 11
  • 《ijs》速成开发手册3.0 官方用户交流:iApp开发交流(1) 239547050iApp开发交流(2) 10...
    叶染柒丶阅读 5,028评论 0 7