DELPHI盒子
!实时搜索: 盒子论坛 | 注册用户 | 修改信息 | 退出
检举帖 | 全文检索 | 关闭广告 | 捐赠
技术论坛
 用户名
 密  码
自动登陆(30天有效)
忘了密码
≡技术区≡
DELPHI技术
lazarus/fpc/Free Pascal
移动应用开发
Web应用开发
数据库专区
报表专区
网络通讯
开源项目
论坛精华贴
≡发布区≡
发布代码
发布控件
文档资料
经典工具
≡事务区≡
网站意见
盒子之家
招聘应聘
信息交换
论坛信息
最新加入: ajmly
今日帖子: 30
在线用户: 18
导航: 论坛 -> DELPHI技术 斑竹:liumazi,sephil  
作者:
男 badwood (badwood) ★☆☆☆☆ -
盒子活跃会员
2014/6/25 10:48:32
标题:
一个XE5里utf8编码后再解码出现乱码的问题 浏览:2504
加入我的收藏
楼主: 字符串 “2013年9月证券从业资格考试” 编码后再解码就出现乱码了,请问是什么原因。

我用Tencoding来处理编码转换,是哪里写错了吗?
因为除了UTF8,还会用该函数处理其他codepage,如日文韩文德文等,所以希望尽量用Tencoding解决。

测试函数如下:
var
  Aencoding:Tencoding;
  astr:RawByteString;
begin

  Aencoding:=Tencoding.GetEncoding(CP_UTF8);
  astr:=stringof(Aencoding.GetBytes(memo1.Text));
  memo2.Text:=astr;
  Aencoding:= Tencoding.GetEncoding(CP_UTF8);
  memo3.Text:=Aencoding.GetString(bytesof(astr));
  memo4.text:=utf8decode(astr);

end;

结果如图:
此帖子包含附件:
PNG 图像
大小:5.4K
----------------------------------------------
-
作者:
男 crystalmoon (crystalmoon) ★☆☆☆☆ -
盒子活跃会员
2014/6/25 11:03:32
1楼: 请参考我原来提的问题:http://bbs.2ccc.com/topic.asp?topicid=449312
----------------------------------------------
-
作者:
男 star5 (星五) ★☆☆☆☆ -
盒子活跃会员
2014/6/25 12:07:23
2楼:
此帖子包含附件:
JPEG 图像
大小:148.3K
----------------------------------------------
博客 - http://offeu.com
脚本模型 - http://webpascal.com
需要短信接口的请联系我,可发行业与营销内容。
作者:
男 badwood (badwood) ★☆☆☆☆ -
盒子活跃会员
2014/6/25 12:11:17
2楼: 你那个是测试样本就有问题,我这个不一样啊,是 先将一个正常字符串编码后立即再解码 结果就不对
----------------------------------------------
-
作者:
男 badwood (badwood) ★☆☆☆☆ -
盒子活跃会员
2014/6/25 12:18:33
3楼: TO star5 

在XE5里用uft8encode的结果都不对,生成都字符串都没编码,

例如“证券从业资格考试”,UTF8编码后在memo里应该显示为“璇佸埜浠庝笟璧勬牸鑰冭瘯”
此帖子包含附件:
PNG 图像
大小:5.0K
----------------------------------------------
-
作者:
男 star5 (星五) ★☆☆☆☆ -
盒子活跃会员
2014/6/25 12:19:09
3楼: 希望,你能看的懂。
此帖子包含附件:
JPEG 图像
大小:372.6K
----------------------------------------------
博客 - http://offeu.com
脚本模型 - http://webpascal.com
需要短信接口的请联系我,可发行业与营销内容。
作者:
男 star5 (星五) ★☆☆☆☆ -
盒子活跃会员
2014/6/25 12:23:48
4楼: Memo5.Lines.Text := string(
Web.HTTPApp.HTTPEncode(//这里不用加AnsiString的
System.UTF8Encode(Memo1.Lines.Text)
)
);

string>utf8encode>urlencode>string
string>urldecode>utf8decode>string
----------------------------------------------
博客 - http://offeu.com
脚本模型 - http://webpascal.com
需要短信接口的请联系我,可发行业与营销内容。
作者:
男 wr960204 (武稀松) ★☆☆☆☆ -
盒子活跃会员
2014/6/25 12:24:02
3楼: 似乎你对Unicode和Delphi的Encoding还有Unicode和RawByteString之类的概念完全是混乱的.
var
  Aencoding:Tencoding;
  astr:RawByteString;
begin

  //好多错误
  //1.StringOf和BytesOf是为了简化用系统默认编解码器编解码用的.你的UTF8不合适
  //2. astr:=Aencoding.GetString这种有问题,因为GetString返回的是UnicodeString,而你的astr是RawBytString,那么实际上会有一层转换.astr里面放的是UTF16转过来的ANSI字符串.不含任何编码
  Aencoding:=StringOf(CP_UTF8);
  astr:=Aencoding.GetString(Aencoding.GetBytes(memo1.Text));  //1,2错误都犯了 Stringof是使用Windows默认的,UTF16来编码,你的Bytes是UTF8编码能不乱掉吗.StringOf换成Aencoding.GetString
  memo2.Text:=astr;
  Aencoding:= Tencoding.GetEncoding(CP_UTF8);
  memo3.Text:=Aencoding.GetString(bytesof(astr));//参见上面的1 同理,你上面是吧BytesOf换成Aencoding.GetBytes即可
  memo4.text:=utf8decode(astr);  //参见上面的 2

end;
----------------------------------------------
武稀松http://www.raysoftware.cn
作者:
男 star5 (星五) ★☆☆☆☆ -
盒子活跃会员
2014/6/25 12:30:10
5楼: 武稀松解释清楚了。
----------------------------------------------
博客 - http://offeu.com
脚本模型 - http://webpascal.com
需要短信接口的请联系我,可发行业与营销内容。
作者:
男 badwood (badwood) ★☆☆☆☆ -
盒子活跃会员
2014/6/25 12:42:08
6楼: 谢谢武稀松 ,问题解决了

不过关于RawByteString有点糊涂了

Enables the passing of string data of any code page without doing any codepage conversions. 

理解为不做任何转换
----------------------------------------------
-
作者:
男 crystalmoon (crystalmoon) ★☆☆☆☆ -
盒子活跃会员
2014/6/25 12:48:59
7楼: to badwood ,其实是一样的,就是多了一个Base64而已,也是把Default的字符串先转成big5,utf8之类的,然后 再Base64,反之,再切回来,看来你还是没有仔细看到底。
----------------------------------------------
-
作者:
男 badwood (badwood) ★☆☆☆☆ -
盒子活跃会员
2014/6/25 14:07:36
8楼: 谢谢
----------------------------------------------
-
作者:
男 badwood (badwood) ★☆☆☆☆ -
盒子活跃会员
2014/6/25 17:11:16
9楼: 之前以为解决了,但后来仔细研究武稀松的说明,又糊涂了。

 Aencoding:=Tencoding.GetEncoding(CP_UTF8);
 astr:=Aencoding.GetString(Aencoding.GetBytes(memo1.Text)); 

这样不是什么也没做吗,没有将字符串进行转码,还是我没有领会武大的意思?

TO crystalmoon 
我之前用的stingof 和bytesof,它们就是调用 tencoding.default.getstring 和 tencoding.default.getbytes,和你的代码并无不同。
----------------------------------------------
-
作者:
男 crystalmoon (crystalmoon) ★☆☆☆☆ -
盒子活跃会员
2014/6/25 22:01:43
10楼: 我没用tencoding.default.getstring,我都是 TEncoding.GetEncoding(XXX).GetString(OutStr.Bytes),如果是用Default,指的是用你系统的本地代码页来解码,一般都是GB2312(CP936)...
另外,我那个连接讨论最后的tintin1943就有代码。
还有你上面的说有没有做的问题,其实星五哥的图片已经给你写的很清楚了。
为什么显示上是一样的,主要是因为你用的UTF-8,而XE5原生就直接Unicode的。。你用HTTPEncode或者Base64之类的再加密一下,就能看出其实是不一样的。
----------------------------------------------
-
作者:
男 badwood (badwood) ★☆☆☆☆ -
盒子活跃会员
2014/6/26 0:37:45
11楼: 1、用tencoding.default.getstring 和用TEncoding.GetEncoding(936).GetString是一回事呢。

2、tfilestream不指定codepage,它的bytes,就是tencoding.default.getbytes,你的那个帖子里的OutStr.Bytes实际就是通过tencoding.default.getbytes获得的,等同bytesof


3、star5用的utf8encode,生成的确实是正确编码了,但不是我想要的,我咨询的是tencoding的使用。

4、按武大指点的

 Aencoding:=Tencoding.GetEncoding(CP_UTF8);
 astr:=Aencoding.GetString(Aencoding.GetBytes(memo1.Text));
实际等于没做编码,用httpencode查看了memo1.text和astr的值,是一样的。

我困惑就是这里,应该是没正确理解武大的意思吧。
此帖子包含附件:
PNG 图像
大小:14.3K
----------------------------------------------
-
作者:
男 badwood (badwood) ★☆☆☆☆ -
盒子活跃会员
2014/6/26 0:44:03
12楼:
bs:=Tencoding.GetEncoding(CP_UTF8).GetBytes(astr)

获得的tbytes结果是没有问题的,转码正确。

问题就是出在怎么正确将tbytes转为string上。


因为我写的代码,使用的是stringof(等于Tencoding.GetEncoding(936).Getstring)来转tbytes,测试时,发现部分中文字符串会出错。

希望能有一个正确的代码参考一下。
----------------------------------------------
-
作者:
男 crystalmoon (crystalmoon) ★☆☆☆☆ -
盒子活跃会员
2014/6/26 1:20:22
13楼: 你还是没明白我的意思,我在那个代码中用936是因为要装 将Big5编码转成gb2312,而你这里开始是要转UTF-8,那么就应该用GetEncoding(65001)...
自己看,再不明白就没办法了。。。
此帖子包含附件:
PNG 图像
大小:41.4K
----------------------------------------------
-
作者:
男 crystalmoon (crystalmoon) ★☆☆☆☆ -
盒子活跃会员
2014/6/26 1:20:40
14楼: 结果如下:
此帖子包含附件:
PNG 图像
大小:45.2K
----------------------------------------------
-
作者:
男 badwood (badwood) ★☆☆☆☆ -
盒子活跃会员
2014/6/26 1:49:51
15楼: 谢谢你的帮助,

我们使用的方法其实一直是相同的。

前面我提到的了,出错在于将tbytes转为string的步骤。

你用的是bytestorawstr 将tbytes转为 rawbytestring,结果当然没错,因为 TBYTES的结果本来就是对的。

重点是,我不知道如何正确将 tbytes转为 string,或者将 rawbytestring 转为 string
----------------------------------------------
-
作者:
男 badwood (badwood) ★☆☆☆☆ -
盒子活跃会员
2014/6/26 2:18:37
16楼: 参照utf8encode里的代码,将rawbytestring 做如下处理,能正确转为string了

  if rawbytestr <> '' then
  PStrRec(PByte(rawbytestr) - SizeOf(StrRec)).codePage := CP_UTF8;

不知道还有没有其他标准的方法
----------------------------------------------
-
作者:
男 crystalmoon (crystalmoon) ★☆☆☆☆ -
盒子活跃会员
2014/6/26 10:24:25
17楼: 嗯,因为rawbytestring本身不指定代码页,在显示时程序无法根据代码页来正确显示在界面上,上面的代码只是告诉程序正确显示的方式,对本身的内容不作任何的改变,所以用不用上面的代码,对HTTPEncode,Base64等函数的结果是没有影响的。
----------------------------------------------
-
信息
登陆以后才能回复
Copyright © 2CCC.Com 盒子论坛 v3.0.1 版权所有 页面执行136.7188毫秒 RSS