对UTF-8和GB2312格式 URL进行解码
新的系统编码格式是:UTF-8
老的页面编码格式是: GB2312
新的系统的URL参数(带中文) 提交到老的系统中,中文参数是乱码。
解决思路1,在新的系统中传递的时候使用JS进行解码,然后再编码。这种方案,和浏览器本身传参无区别。所以,在使用这种方案后,在老的系统中解码,依然解决不了问题。
简单写一下实现的伪代码
传参的时候,使用JS 编码:location.href="old.aspx?word="+encodeURI('中文')
Server.UrlDecode(Request["word"]);
最终还是乱码。
最终看了一下编过的汉字:“中文”
UTF-8下:
JS编码过的如下: %E4%B8%AD%E5%9B%BD
浏览器FORM提交的如下:%E4%B8%AD%E5%9B%BD
GB2312:
JS编码格式如下: %E4%B8%AD%E5%9B%BD
浏览器FORM提交的如下:%D6%D0%B9%FA
说明,使用JS编码模式都是将字符串用UTF-8模式下编码。
如果这样子的话,那我使用JS编码传参,后台都采用UTF-8进行解码就可以了。(这种思路未测试,我自己使用的是思路2)
HttpUtility.UrlDecode(strEncode, Encoding.UTF8); //判断编码格式 UTF-8
解决思路2,
既然是解码的问题,那我就要针对传过来的的字符串进行判断,然后进行相应的格式进行解码。
(1).判断其编码格式。
(2).再解码。
代码如下:
//string strEncode =Request["word"]; //解码的时候这样子获取参数是有问题的,这样获取参数,无论怎么转都是乱码。应用下面的这种方式
string strEncode =GetWord( Request.ServerVariables["QUERY_STRING"]);
if (IsUTF8(strEncode)) result = HttpUtility.UrlDecode(strEncode, Encoding.UTF8); //判断编码格式 UTF-8
else result = HttpUtility.UrlDecode(strEncode, Encoding.GetEncoding("GB2312")); 判断编码格式 GB2312
///
/// 获取word参数
///
///
///
private string GetWord(string value)
{
if (string.IsNullOrEmpty(value)) return "";
string[] array = value.Split('&');
string strEncode = "";
for (int i = 0; i < array.Length; i++)
{
if (array[i].IndexOf("word=") >= 0)
{
strEncode = array[i].Replace("word=", "");
break;
}
}
return strEncode;
}
///
/// 获取字符的字节
///
///
///
private static byte[] GetUrlCodingToBytes(string url)
{
StringBuilder sb = new StringBuilder();
int i = url.IndexOf('%');
while (i >= 0)
{
if (url.Length < i + 3)
{
break;
}
sb.Append(url.Substring(i, 3));
url = url.Substring(i + 3);
i = url.IndexOf('%');
}
string urlCoding = sb.ToString();
if (string.IsNullOrEmpty(urlCoding))
return new byte[0];
urlCoding = urlCoding.Replace("%", string.Empty);
int len = urlCoding.Length / 2;
byte[] result = new byte[len];
len *= 2;
for (int index = 0; index < len; index++)
{
string s = urlCoding.Substring(index, 2);
int b = int.Parse(s, System.Globalization.NumberStyles.HexNumber);
result[index / 2] = (byte)b;
index++;
}
return result;
}
///
/// 判断字符是否为UTF-8
///
///
///
private static bool IsUTF8(string url)
{
byte[] buf = GetUrlCodingToBytes(url);
int i;
byte cOctets; // octets to go in this UTF-8 encoded character
bool bAllAscii = true;
long iLen = buf.Length;
cOctets = 0;
for (i = 0; i < iLen; i++)
{
if ((buf[i] & 0x80) != 0) bAllAscii = false;
if (cOctets == 0)
{
if (buf[i] >= 0x80)
{
do
{
buf[i] <<= 1;
cOctets++;
}
while ((buf[i] & 0x80) != 0);
cOctets--;
if (cOctets == 0)
return false;
}
}
else
{
if ((buf[i] & 0xC0) != 0x80)
return false;
cOctets--;
}
}
if (cOctets > 0)
return false;
if (bAllAscii)
return false;
return true;
}
2012-8-3 16:20
今天,遇到一个问题,MVC项目中,一个AJAX请求的问题,又是乱码。肯定又是编码的东西,搞的人难受。其实很简答,一个文本框,输入一个值。AJAX请求一下,看是否存在,如果存在就清空。看前任写的代码,
function checkUnitName(unitName) {
if (unitName != "") {
$.get("/Manage/Product/CheckUnitName", { pUnitName: encodeURI(unitName) }, function (data) {
if (data == "0") {
alert("单位名称已经存在,请选择");
$("#UnitName").val("");
}
});
}
}
public static string UNEscape(string str)
{
string outstr = "";
#region 老方法
if (!string.IsNullOrEmpty(str))
{
string[] strlist = str.Replace("%", "").Split('u');
try
{
for (int i = 1; i < strlist.Length; i++)
{
//将unicode字符转为10进制整数,然后转为char中文字符
outstr += (char)int.Parse(strlist[i].Substring(0, 4), System.Globalization.NumberStyles.HexNumber);
}
}
catch (FormatException ex)
{
outstr = ex.Message;
}
}
#endregion
return outstr;
}
这个方法基本没派上用场,执行过后,返回为 空字符串。
其实就这一句话就搞定了。
public static string UNEscape(string str)
{
string outstr = outstr = HttpUtility.UrlDecode(str, Encoding.UTF8);
return outstr;
}
AJAX乱码问题
从网上查资料得知,
1、xtmlhttp 返回的数据默认的字符编码是utf-8,
2、post方法提交数据默认的字符编码是utf-8, (get也是的,自己就是使用get方式)
因为我这个项目是使用GB2312的编码格式,AJAX (UTF-8) 的模式传到后台,就会出现乱码了。明白了其中的道理,问题就好解决了。