BIG5码到GB码转换技术
# u8 \& K2 W R v) y( w/ `一起学习 中文因为数量太多,所以与英文用ASCII码一个字节表示不同,它使用两个字节来表示。通过计算这两个字节,我们可以得到其表示的汉字在中文字库中的位置。读取该位置的若干字节,以获得表示这个汉字的点阵信息。有了这些信息,就可以分别在DOS或WINDOWS中显示该汉字。事实上,在文本文件中保存的就是每个汉字对应的两个字节编码,而显示问题由中文操作系统自动解决。# W3 l6 ^$ q, c5 ]7 ?2 O0 W2 N
% V6 j0 G, g/ P8 F% L& q
汉字编码并不统一,我们使用的是GB码,而台湾地区使用的是BIG5码。BIG5码文件中保存的是汉字相应的BIG5编码,GB码文件中保存的是汉字相应的GB编码(这也就是“乱码现象”的来由)。所以转换工作的关键是有一个记录每个BIG5编码对应GB编码的码表文件。7 t4 N/ Y, g* N! R. w
/ Z7 P' Q: R3 j) h3 ]
第一步 制作码表文件
6 o, G! M' ]! r8 X# k4 L* A5 H! D5 T5 `, O
BIG5码编码规则是这样的:每个汉字由两个字节构成,第一个字节的范围从0X81-0XFE,共126种。第二个字节的范围分别为0X40-0X7E,0XA1-0XFE,共157种。也就是说,利用这两个字节共可定义出 126 * 157=19782种汉字。这些汉字的一部分是我们常用到的,如一、丁,这些字我们称为常用字,其BIG5码的范围为0XA440-0XC671,共5401个。较不常用的字,如滥、调,我们称为次常用字,范围为 0XC940-0XF9FE,共7652个,剩下的便是一些特殊字符。7 @2 i! V/ l j" c0 |) T
制作码表文件的原理是这样的:首先将所有的BIG5编码写入一个文件,然后,使用具有BIG5码到GB码转换功能的软件,如地球村、东方快车、四通利方,将文件转换为GB码文件,即得到码表文件。
% K, c/ ?, A; u7 _1 O% O" c
6 ]4 |! H' L! \2 B* r2 y+ I/ D 下面的源程序将所有可能的BIG5编码(0XA100-0XFEFF)写入文件“Table.TXT”。; X- M% A' @ A' g- B q0 E) i5 j
- o4 a" r& X$ d0 r/ O( f4 T//TURBO C 3.0
1 y- p, r m& i, k8 t' U) S#include <Stdio.h> x" ?5 H% j5 U3 w5 \
#include <stdlib.h>
" ^9 X; A: M$ O O* Y7 Wvoid main(){
/ G3 M6 B/ X' b- v+ T+ @FILE * codefile;
, Z9 r7 U5 ~$ {' r4 p2 Gint I,j,k;
Y8 c& V/ o8 w8 r. ?" e }! y9 bcodefile=fopen("table.txt","w b");5 ^; `* j8 Y3 G/ {2 H" d2 p
for (i=0xa1;i<=0xfe;I ){
r' `% p; _) Q% `3 e4 v) bfor(j=0x00;j<=0xff;j ){! T# E( x+ z! {2 d+ X& r
fwrite(& I,1,1,codefile);
" ~# p- S% h# B% [( |fwrite(& j,1,1,codefile);}
- ^9 @3 p3 w2 [, {1 B$ c}
7 t6 E6 j/ l4 D; y/ Mfclose(codefile);0 f( `7 n0 ^ v9 B" p: z# F
return;
2 Y3 n' l6 N* D8 w# k" {/ Y, _} @# W o4 R+ w+ a
运行地球村、东方快车或四通利方,将“Table.txt”从BIG5码转换为GB码,即获得码表文件。: e9 C; Y* L: `4 k
( N& t7 ?6 q/ w. ?9 _% r
% H: G+ h1 W* V! Q1 a/ i& {$ }& {第二步 转换
" A% k( Z- g4 i% L# [- a P9 S; ^# }4 k/ _& E* F9 ]
// 本文转自 C Builder研究 - http://www.ccrun.com/article.asp?i=166&d=8dgfdd
+ \. [2 R! C5 n x+ \5 x4 h 下面的源程序,将BIG5码文件转换为GB码文件。: `: h+ _; v/ p3 }1 X! e
& X6 T) f; G* K ]% ^( x//TURBO C 3.0" [- U& W" E7 {- h/ Y2 _
#include <stdio.h>
" S0 d! ], y0 D) k3 }5 k3 C#include <stdlib.h>
7 B! }* x2 p6 r0 h8 z$ V/ x) I" @void main(){8 H; H- @7 ?1 D
int que, wei;
4 }$ Y/ Y- {1 ]( uFILE * sourcefile;( J% Q) i6 a9 P; B; u; t% q9 Z) d
FILE * tabfile;7 v- j; U1 N3 y r _' k8 }6 [
FILE * destfile;4 t) J% m. {+ Y8 _
sourcefile = fopen("big.txt', "r b");3 `, R2 m4 ^* m8 e& y
//BIG5 码文件
7 J r7 g/ n2 J" w% Q. S/ itabfile = fopen("table.txt", 'r b");) o+ E/ J2 f9 q, Y+ Q H1 F8 K
//码表文件/ @# b" b! R' W; f( ^. S# Z/ T5 \
destfile = fopen("gb.txt","w b");
4 U7 b1 A0 s, w+ x+ @//转换生成的GB码文件2 R V2 E0 p8 T# P( J1 O
while (!feof(sourcefile)){
# l5 ^! @* M6 r- mfread(& que,1,1,sourcefile);: A' U5 i- q8 k- w
if (feof(sourcefile)){
5 X: g; W9 m! C2 }break; }/ _4 [% J" y. _& e9 I
if (que> =0xa1 && que <=0xfe)9 L+ y) G T1 C6 `% x: z& I
//叛断是否汉字(BIG5编码)
) x' W1 I; J+ ]/ b! w! ~{fread(& wei,1,1,sourcefile);
* p y5 P4 v/ n4 j& Eif (wei<0xa1) wei = wei - 0x40;: q2 ?/ S# V1 \6 A! r; X+ `4 I
if (wei>=0xa1) wei = wei - 0xa1 0x7e - 0x40 1; z" L$ l" v5 u/ y( r" D
fseek(tabfile, 2 * ((que -0xa1) * (0xfe - 0xa1 1 0x7e - 0x40 1 ) wei), SEEK_SET);/ |. M" j& o$ N, Z
fread(& que,1,1,tabfile);
, ]0 M, ^7 ?2 s( S- Y: cfread(& wei,1,1,tabfile);
7 e( T- d0 q! _* pfwrite(& que,1,1,destfile);0 D6 n5 p* c& U6 M
fwrite(& wei,1,1,destfile);
, M+ q/ }7 @/ g* L: o2 u7 @* S}
; p1 d M, @9 V1 j* f4 t L& @0 }else" x# E! x! b6 l: ` d
fwrite(& que,1,1,destfile); //处理英文
1 |" n3 T2 b T& I! |1 m}
2 u4 d: z5 Y& h/ ]7 Ufclose(sourcefile);
8 U9 Z+ f) V5 \4 X* Y; W0 s) R/ nfclose(tabfile);
6 p, X4 c! `$ q8 p! P* M b& pfclose(destfile);- p. q' t0 z, n+ u6 n
return;
/ Y5 w- t6 {' d$ O. k}5 g& e/ \" d4 ~8 H- p
m _. f- p* M+ d 以上程序在Win95/97,TC3.0 通过。稍加修改,也可用于CB、VC或VB程序中。用同样的方法,我们也可以将GB码转换为BIG5码。 中文因为数量太多,所以与英文用ASCII码一个字节表示不同,它使用两个字节来表示。通过计算这两个字节,我们可以得到其表示的汉字在中文字库中的位置。读取该位置的若干字节,以获得表示这个汉字的点阵信息。有了这些信息,就可以分别在DOS或WINDOWS中显示该汉字。事实上,在文本文件中保存的就是每个汉字对应的两个字节编码,而显示问题由中文操作系统自动解决。- Q* N0 B( `4 }& g3 |/ t
5 Q, S1 |+ E3 U0 k9 _
汉字编码并不统一,我们使用的是GB码,而台湾地区使用的是BIG5码。BIG5码文件中保存的是汉字相应的BIG5编码,GB码文件中保存的是汉字相应的GB编码(这也就是“乱码现象”的来由)。所以转换工作的关键是有一个记录每个BIG5编码对应GB编码的码表文件。
1 y# _! ^7 p* h4 u
: l; d) \) ?; r' }& P- G1 H第一步 制作码表文件
7 p* @ e5 s5 M U7 P$ g: r1 q8 ?# m" `5 p5 a) M
BIG5码编码规则是这样的:每个汉字由两个字节构成,第一个字节的范围从0X81-0XFE,共126种。第二个字节的范围分别为0X40-0X7E,0XA1-0XFE,共157种。也就是说,利用这两个字节共可定义出 126 * 157=19782种汉字。这些汉字的一部分是我们常用到的,如一、丁,这些字我们称为常用字,其BIG5码的范围为0XA440-0XC671,共5401个。较不常用的字,如滥、调,我们称为次常用字,范围为 0XC940-0XF9FE,共7652个,剩下的便是一些特殊字符。
# ?2 \8 y2 J- j6 ~制作码表文件的原理是这样的:首先将所有的BIG5编码写入一个文件,然后,使用具有BIG5码到GB码转换功能的软件,如地球村、东方快车、四通利方,将文件转换为GB码文件,即得到码表文件。
$ w' s6 h9 e' {6 Q+ ] i# ?% y, V6 H) \; y
下面的源程序将所有可能的BIG5编码(0XA100-0XFEFF)写入文件“Table.TXT”。
! ?+ J( g W6 l) k+ C' \- c0 Y m: J" R* @( Z$ o
//TURBO C 3.0
e6 W* e; Q$ M5 P#include <Stdio.h>
0 ?+ _4 q( m5 q/ X9 ]/ J#include <stdlib.h>0 T1 n) g$ ~6 v/ G2 i
void main(){' P. z$ P8 @+ C0 E/ Q3 k1 @
FILE * codefile;
2 G+ g2 {" i6 p. aint I,j,k;
~. Z) a# X5 k( l, P! K* @' ncodefile=fopen("table.txt","w b");
$ s7 u$ K) c L5 O6 Sfor (i=0xa1;i<=0xfe;I ){* w c+ ] K1 T7 ^$ c
for(j=0x00;j<=0xff;j ){3 j: {2 D ~/ g# Q
fwrite(& I,1,1,codefile);
4 B( g. b6 l8 b" E# w6 x& Qfwrite(& j,1,1,codefile);}
" }6 m" a) h6 C; k- b) b2 R, q}+ \4 {7 ]+ C7 R1 K
fclose(codefile);2 b" e+ M8 m6 V3 U8 F, ~1 D
return;
3 j' r$ m9 a! e5 A}
# @! h; G* a- L5 j( b1 h9 \# X0 j 运行地球村、东方快车或四通利方,将“Table.txt”从BIG5码转换为GB码,即获得码表文件。
1 x8 y( w, m& t+ e% x8 H( {3 O: @* p
3 x- p; y6 z# B9 ~+ \ C% @3 f第二步 转换4 K/ b6 u% I# H# i5 E- C$ B
4 C9 ~2 R- K. Q" v7 Y" n
// 本文转自 C Builder研究 - http://www.ccrun.com/article.asp?i=166&d=8dgfdd5 n Z! |: U* e# w
下面的源程序,将BIG5码文件转换为GB码文件。
3 y3 h! c. D6 Z1 n+ Q; n8 Y. q" r1 D) _0 c2 f! [$ ?
//TURBO C 3.0
& I2 ]' F1 n( g0 C0 {1 U; Y9 I#include <stdio.h>
) H5 b) h0 [* v. E9 @) I6 F' X; K#include <stdlib.h>
! Q- I* U4 m& m$ n8 V- k' zvoid main(){
, Y \# G/ O; m% [3 Vint que, wei;
6 }) c$ V+ d8 pFILE * sourcefile;* a( G9 l' k$ a) P
FILE * tabfile;
3 s! x( }1 S( ]* XFILE * destfile;
" d( E9 F8 v" O8 Esourcefile = fopen("big.txt', "r b");
* t0 q$ [$ v* K: W//BIG5 码文件
6 c2 X r; Y( J) ~& W J& ptabfile = fopen("table.txt", 'r b");
& G: x# A0 B1 G5 u; G$ M" X//码表文件
( `1 L8 c% j! U" V7 m' @! Edestfile = fopen("gb.txt","w b");7 J3 ~2 p; U% x& y8 V
//转换生成的GB码文件 |/ F( u+ f& w7 n9 O) }/ m2 S
while (!feof(sourcefile)){ r6 i: j! w) \* ^* `
fread(& que,1,1,sourcefile);/ {9 v. y, e, B3 U3 V
if (feof(sourcefile)){- {. G g6 ~* b6 c
break; }
; v% q5 d9 w+ vif (que> =0xa1 && que <=0xfe)" d J3 j* l ]- A
//叛断是否汉字(BIG5编码)
+ _+ f6 X0 u- V& F{fread(& wei,1,1,sourcefile);3 }+ l. w$ k/ f9 J2 D. d
if (wei<0xa1) wei = wei - 0x40;- _: d% r$ x: ]
if (wei>=0xa1) wei = wei - 0xa1 0x7e - 0x40 1;
& Q" V7 L9 S4 u( ^9 H: Wfseek(tabfile, 2 * ((que -0xa1) * (0xfe - 0xa1 1 0x7e - 0x40 1 ) wei), SEEK_SET);
f/ X. W5 P7 q& Sfread(& que,1,1,tabfile);
4 E8 ~! W c4 h' U( T% A. c$ ffread(& wei,1,1,tabfile);
% A/ t- x! f3 u. Zfwrite(& que,1,1,destfile);5 t8 Z3 ^) \7 U" N1 G: d# ]) n1 m
fwrite(& wei,1,1,destfile);
% Q) q$ O( c$ c% n6 ~8 |% X}& L7 S G( o8 e& x0 A
else
/ n# {) C- [7 P/ l/ v" Mfwrite(& que,1,1,destfile); //处理英文
R) A( y5 @( {; l( @2 x}
f. A( b+ S$ Y* Q6 Dfclose(sourcefile);
- x+ t/ r! {3 Bfclose(tabfile);
3 M; m2 U/ A" a( D( _6 Kfclose(destfile);9 i: \% \. v8 U/ r. h
return;
f' |+ l4 e9 h& r2 d# T}
7 c; b* d- e& H
; m: w$ P5 Q% G6 b0 v' A 以上程序在Win95/97,TC3.0 通过。稍加修改,也可用于CB、VC或VB程序中。用同样的方法,我们也可以将GB码转换为BIG5码。 |