这几天正好遇到这个问题,需要看日文文档,但是在中文环境下是乱码,总是切换语言环境也太麻烦了,干脆想了这个办法,自己写一个转换编码格式的小软件,当然很多技术难点是在csdn找到的,我只是照葫芦画瓢罢了
代码作者:
1.实现任意多字节语言与Unicode的转换:
function UnicodeEncode(Str: string; CodePage: integer): WideString;
var
Len: integer;
begin
Len := Length(Str) + 1;
SetLength(Result, Len);
Len := MultiByteToWideChar(CodePage, 0, PChar(Str), -1, PWideChar(Result), Len);
SetLength(Result, Len - 1); //end is #0
end;
function UnicodeDecode(Str: WideString; CodePage: integer): string;
var
Len: integer;
begin
Len := Length(Str) * 2 + 1; //one for #0
SetLength(Result, Len);
Len := WideCharToMultiByte(CodePage, 0, PWideChar(Str), -1, PChar(Result), Len, nil, nil);
SetLength(Result, Len - 1);
end;
比如,GB2312的代码页是936,则GB2312要转为Unicode可以这样:
UniStr := UnicodeEncode(GBStr, 936);
要从Unicode内码转为GB2312则可以这样:
GBStr := UnicodeDecode(UniStr, 936);
对于其他语言也是一样,只要知道了代码页。
注:日文的代码页是932
2.文件的编码变换
首先看这位大侠的几个提示:
AnsiToUTF8
UTF8ToUnicode
看一下这两个函数的帮助。
你可以用一个TStringList将文本文件Load进来,然后声明一个WideString变量,最后调用上面的StringToWideChar,转换后的信息保存在WideString中。
再声明一个MemoryStream将WideString写进流中。
最后将流保存为一个文本文件。
你去文件文件看,它就是Unicode编码的,且信息一样。
下面是终极版:
每一种格式的文本在最开头都会有一个标识,标识它是什么编码。比如Unicode的最开头就是FFFE。笔记本就 是根据最开头的这个标识来识别它是什么码的。
而你在上面写的时候,没有将这个标识写在文件的最开头,所以你用笔记本打开的时候识别不了,不信你打开之后选另存为,就可以看到它识别为Ansi码了,所以会显示不对。
正确的做法是在文件的开头写进FFFE这个标识,就可以正确显示了。
下面是源码:
var SL: TStringList;
MM: TMemoryStream;
AnStr: String;
WS: WideString;
P: PByteArray;
begin
SL:= TStringList.Create;
MM:= TMemoryStream.Create;
try
SL.LoadFromFile('test.txt');
AnStr:= SL.Text;
WS:= AnStr; //转为Unicode
//文本开头写进Unicode的标识
GetMem(P, 2 * Sizeof(Char));
P[0]:= $FF;
P[1]:= $FE;
MM.Write(P^, 2 * Sizeof(Char));
//将Unicode文本写进流中保存。
MM.Write(PWideChar(WS)^, Length(WS) * Sizeof(WideChar));
MM.SaveToFile('test2.txt');
FreeMem(P);
finally
SL.Free;
MM.Free;
end;
end;
我先在一个笔记本中写下:“yes是的,这是Unicode”,然后保存为Test文件。这个时候它是Ansi编码。
执行我上面的代码之后,文本保存为Test2,这时它就是Unicode码了,可以正确显示,你可选另存为看看它是不是Unicode编码。
然后还有另外一个哥们的发言:
unicode big endian文本文件:头两个字符分别是FE FF(16进制,big endian自然会是相反的)
utf-8文本文件:头两个字符分别是EF BB(16进制) (补充:如果想通过写入文件头来标识utf-8编码文件,则需要写入Write(LogFile,#$EF#$BB#$BF);)
可以用记事本打开一个文本文件,以各种方式另存为,再用16进制编辑器就可以看到了。
代码作者:
linzhengqun(风。我回来了)
下面是相关源码:1.实现任意多字节语言与Unicode的转换:
function UnicodeEncode(Str: string; CodePage: integer): WideString;
var
Len: integer;
begin
Len := Length(Str) + 1;
SetLength(Result, Len);
Len := MultiByteToWideChar(CodePage, 0, PChar(Str), -1, PWideChar(Result), Len);
SetLength(Result, Len - 1); //end is #0
end;
function UnicodeDecode(Str: WideString; CodePage: integer): string;
var
Len: integer;
begin
Len := Length(Str) * 2 + 1; //one for #0
SetLength(Result, Len);
Len := WideCharToMultiByte(CodePage, 0, PWideChar(Str), -1, PChar(Result), Len, nil, nil);
SetLength(Result, Len - 1);
end;
比如,GB2312的代码页是936,则GB2312要转为Unicode可以这样:
UniStr := UnicodeEncode(GBStr, 936);
要从Unicode内码转为GB2312则可以这样:
GBStr := UnicodeDecode(UniStr, 936);
对于其他语言也是一样,只要知道了代码页。
注:日文的代码页是932
2.文件的编码变换
首先看这位大侠的几个提示:
AnsiToUTF8
UTF8ToUnicode
看一下这两个函数的帮助。
你可以用一个TStringList将文本文件Load进来,然后声明一个WideString变量,最后调用上面的StringToWideChar,转换后的信息保存在WideString中。
再声明一个MemoryStream将WideString写进流中。
最后将流保存为一个文本文件。
你去文件文件看,它就是Unicode编码的,且信息一样。
下面是终极版:
每一种格式的文本在最开头都会有一个标识,标识它是什么编码。比如Unicode的最开头就是FFFE。笔记本就 是根据最开头的这个标识来识别它是什么码的。
而你在上面写的时候,没有将这个标识写在文件的最开头,所以你用笔记本打开的时候识别不了,不信你打开之后选另存为,就可以看到它识别为Ansi码了,所以会显示不对。
正确的做法是在文件的开头写进FFFE这个标识,就可以正确显示了。
下面是源码:
var SL: TStringList;
MM: TMemoryStream;
AnStr: String;
WS: WideString;
P: PByteArray;
begin
SL:= TStringList.Create;
MM:= TMemoryStream.Create;
try
SL.LoadFromFile('test.txt');
AnStr:= SL.Text;
WS:= AnStr; //转为Unicode
//文本开头写进Unicode的标识
GetMem(P, 2 * Sizeof(Char));
P[0]:= $FF;
P[1]:= $FE;
MM.Write(P^, 2 * Sizeof(Char));
//将Unicode文本写进流中保存。
MM.Write(PWideChar(WS)^, Length(WS) * Sizeof(WideChar));
MM.SaveToFile('test2.txt');
FreeMem(P);
finally
SL.Free;
MM.Free;
end;
end;
我先在一个笔记本中写下:“yes是的,这是Unicode”,然后保存为Test文件。这个时候它是Ansi编码。
执行我上面的代码之后,文本保存为Test2,这时它就是Unicode码了,可以正确显示,你可选另存为看看它是不是Unicode编码。
然后还有另外一个哥们的发言:
warmworm(warmworm)
厚厚
以前我也为ansi和unicode的转换,看遍了这些函数,其实最简单的方法
就是
Ansi->Unicode
strUnicode := WideString(strAnsi);
Unicode->Ansi
strAnsi := AnsiString(strUnicode);
aiirii(ari-http://spaces.msn.com/members/aiirii/)
unicode文本文件:头两个字符分别是FF FE(16进制)unicode big endian文本文件:头两个字符分别是FE FF(16进制,big endian自然会是相反的)
utf-8文本文件:头两个字符分别是EF BB(16进制) (补充:如果想通过写入文件头来标识utf-8编码文件,则需要写入Write(LogFile,#$EF#$BB#$BF);)
可以用记事本打开一个文本文件,以各种方式另存为,再用16进制编辑器就可以看到了。