汉字转拼音问题

汉字转拼音问题

    这是一个非常经典的问题,同时,也是一个很难解决的问题。经典是因为,这个问题非常常见,而且有很多解决方案。

难以解决是因为,存在多音字。可以发现很多股票软件都有这问题,比如zgyh 出来的不是中国银行,而是找不到,

这是因为,中国银行的 “行” 查出来读的是 "xing" 。我篇文章我只是提供了一个原始的转换方法,就是查表。

和你以前看过的算法可能不一样的是,我加了一个二分查找,我看到的一个开源的解决方案是顺序查找的。

    关于,多音字问题,我只有一个小规模的多音字表,从所有股票名称里面纠正过来的。解决方案是这样的:在查找拼音的时候,

查找一下这个字是否在多音字表里面,如果是,那么查找前后组成的词,来决定读什么。如果有谁有完整的多音字表,或者有更好的

解决方案,请给我留言。我一定拜谢。

 

ExpandedBlockStart.gif 代码
<? php
/* *
 * 初始化
 *
 * @param string $file 拼音代码对应表
 * @return array 把这个对应表映射成array的格式
 
*/
function  pinyin_init( $file )
{
    
$pinyin   =   file ( $file );
    
if  ( empty ( $pinyin )) {
        
throw   new   Exception ( " load pinyin table error. " );
    }
    
foreach  ( $pinyin   as   $k   =>   $item )
    {
        
$item   =   explode ( " \t " ,   $item );
        
$item [ 0 =   trim ( $item [ 0 ]);
        
$item [ 1 =  (int) trim ( $item [ 1 ]);
        
$pinyin [ $k =   $item ;
    }
    
$pinyin []  =   array ( '' ,   - 10248 );  // 最后一个拼音的妈是 -10247
     return   $pinyin ;
}

/* *
 * 查找一个字符串中,中文字符部分的拼音
 *
 * @param array $pingyin
 * @param string $str       字符串
 * @param string $in_encode 字符串的编码
 * @return array
 
*/
function  pingyin_get( $pingyin ,   $str ,   $in_encode   =   ' gb2312 ' )
{
    
if  ( strtolower ( $in_encode !=   ' gb2312 ' ) {
       
$str   =   iconv ( $in_encode ,   ' gb2312 ' ,   $str );
       
if  ( ! $str ) {
           
throw   new   Exception ( ' invalid input string. ' );
       }
    }
    
$pinyin_arr   =   array ();
    
$len   =   strlen ( $str );
    
for  ( $i   =   0 $i   <   $len $i ++ )
    {
        
if  ( $i   ==   $len   - 1 break ;
        
if  (( $code   =  pinyin_getcode_( $str [ $i ] ,   $str [ $i   +   1 ]))  !=   false ) {
            
$i ++ ;
            
if  (( $py   =  pinyin_find_( $pingyin ,   $code ))  !==   false ) {
                
$pinyin_arr [ substr ( $str ,   $i   -   1   ,   2 )]  =   $py ;
            }
        }
    }
    
return   $pinyin_arr ;
}

/* *
 * 内部函数,通过拼音码查找汉字
 *
 * @param array $pingyin
 * @param int $code
 * @return string/false 
 
*/
function  pinyin_find_( $pingyin ,   $code )
{
    
$start   =   0 ;
    
$count   =   count ( $pingyin -   1 ;
    
$end   =   $count ;
    
if  ( $code   <   $pingyin [ 0 ][ 1 ||   $code   >=   $pingyin [ $end ][ 1 ]) {  // no found.
         return   false ;
    }
    
while  ( $start   <=   $end )
    {
        
$mid   =  (int)( $start   +  ( $end   -   $start ) / 2 );
        
if  ( $mid   ==   $count ) {  // 正常情况下,应该是永远都不会执行到这里,但是为了逻辑上清晰点,还是决定写上
             return   $pingyin [ $mid   -   1 ][ 0 ];
        } 
else   if  ( $code   >=   $pingyin [ $mid ][ 1 &&   $code   <   $pingyin [ $mid   +   1 ][ 1 ]) {
            
return   $pingyin [ $mid ][ 0 ];
        } 
else   if  ( $code   >=   $pingyin [ $mid   +   1 ][ 1 ]) {
           
$start   =   $mid   +   1 ;
        } 
else  {
            
$end   =   $mid   -   1 ;
        }
    }
    
return   false ;
}

/* *
 * 内部函数,通过汉字的第一个字节 和 第二个字节,得到查找的code
 *
 * @param char $ch1
 * @param char $ch2
 * @return int
 
*/
function  pinyin_getcode_( $ch1 ,   $ch2 )
{
    
$num1   =   ord ( $ch1 );
    
$num2   =   ord ( $ch2 );
    
if  ( $num1   >   159   &&   $num1   <   248 ) {
        
return   $num1   *   256   +   $num2   -   65536 ;
    }
    
return   false ;
}

/* *
 * 基本配置信息
 
*/
define ( " CURRENT_PATH " ,   dirname ( __FILE__ ));
$pingin_file   =  CURRENT_PATH  .   " /gb-pinyin.table " ;

$pinyin   =  pinyin_init( $pingin_file );
$py   =  pingyin_get( $pinyin ,   " 中国银行 " ,   ' utf-8 ' );
echo   iconv ( ' gb2312 ' ,   ' utf-8 ' ,   print_r ( $py ,   true ));
echo   implode ( " ' " ,   $py );
?>

 

拼音表如下:

ExpandedBlockStart.gif 代码
- 20319
ai 
- 20317
an 
- 20304
ang 
- 20295
ao 
- 20292
ba 
- 20283
bai 
- 20265
ban 
- 20257
bang 
- 20242
bao 
- 20230
bei 
- 20051
ben 
- 20036
beng 
- 20032
bi 
- 20026
bian 
- 20002
biao 
- 19990
bie 
- 19986
bin 
- 19982
bing 
- 19976
bo 
- 19805
bu 
- 19784
ca 
- 19775
cai 
- 19774
can 
- 19763
cang 
- 19756
cao 
- 19751
ce 
- 19746
ceng 
- 19741
cha 
- 19739
chai 
- 19728
chan 
- 19725
chang 
- 19715
chao 
- 19540
che 
- 19531
chen 
- 19525
cheng 
- 19515
chi 
- 19500
chong 
- 19484
chou 
- 19479
chu 
- 19467
chuai 
- 19289
chuan 
- 19288
chuang 
- 19281
chui 
- 19275
chun 
- 19270
chuo 
- 19263
ci 
- 19261
cong 
- 19249
cou 
- 19243
cu 
- 19242
cuan 
- 19238
cui 
- 19235
cun 
- 19227
cuo 
- 19224
da 
- 19218
dai 
- 19212
dan 
- 19038
dang 
- 19023
dao 
- 19018
de 
- 19006
deng 
- 19003
di 
- 18996
dian 
- 18977
diao 
- 18961
die   - 18952
ding 
- 18783
diu 
- 18774
dong 
- 18773
dou 
- 18763
du 
- 18756
duan 
- 18741
dui 
- 18735
dun 
- 18731
duo 
- 18722
- 18710
en 
- 18697
er 
- 18696
fa 
- 18526
fan 
- 18518
fang 
- 18501
fei 
- 18490
fen 
- 18478
feng 
- 18463
fo 
- 18448
fou 
- 18447
fu 
- 18446
ga 
- 18239
gai 
- 18237
gan 
- 18231
gang 
- 18220
gao 
- 18211
ge 
- 18201
gei 
- 18184
gen 
- 18183
geng 
- 18181
gong 
- 18012
gou 
- 17997
gu 
- 17988
gua 
- 17970
guai 
- 17964
guan 
- 17961
guang 
- 17950
gui 
- 17947
gun 
- 17931
guo 
- 17928
ha 
- 17922
hai 
- 17759
han 
- 17752
hang 
- 17733
hao 
- 17730
he 
- 17721
hei 
- 17703
hen 
- 17701
heng 
- 17697
hong 
- 17692
hou 
- 17683
hu 
- 17676
hua 
- 17496
huai 
- 17487
huan 
- 17482
huang 
- 17468
hui 
- 17454
hun 
- 17433
huo 
- 17427
ji 
- 17417
jia 
- 17202
jian 
- 17185
jiang 
- 16983
jiao 
- 16970
jie 
- 16942
jin 
- 16915
jing 
- 16733
jiong 
- 16708
jiu 
- 16706
ju 
- 16689
juan 
- 16664
jue 
- 16657
jun 
- 16647
ka 
- 16474
kai 
- 16470
kan 
- 16465
kang 
- 16459
kao 
- 16452
ke 
- 16448
ken 
- 16433
keng 
- 16429
kong 
- 16427
kou 
- 16423
ku 
- 16419
kua 
- 16412
kuai 
- 16407
kuan 
- 16403
kuang 
- 16401
kui 
- 16393
kun 
- 16220
kuo 
- 16216
la 
- 16212
lai 
- 16205
lan 
- 16202
lang 
- 16187
lao 
- 16180
le 
- 16171
lei 
- 16169
leng 
- 16158
li 
- 16155
lia 
- 15959
lian 
- 15958
liang 
- 15944
liao 
- 15933
lie 
- 15920
lin 
- 15915
ling 
- 15903
liu 
- 15889
long 
- 15878
lou 
- 15707
lu 
- 15701
lv 
- 15681
luan 
- 15667
lue 
- 15661
lun 
- 15659
luo 
- 15652
ma 
- 15640
mai 
- 15631
man 
- 15625
mang 
- 15454
mao 
- 15448
me 
- 15436
mei 
- 15435
men 
- 15419
meng 
- 15416
mi 
- 15408
mian 
- 15394
miao 
- 15385
mie 
- 15377
min   - 15375
ming 
- 15369
miu 
- 15363
mo 
- 15362
mou 
- 15183
mu 
- 15180
na 
- 15165
nai 
- 15158
nan 
- 15153
nang 
- 15150
nao 
- 15149
ne 
- 15144
nei 
- 15143
nen 
- 15141
neng 
- 15140
ni 
- 15139
nian 
- 15128
niang 
- 15121
niao 
- 15119
nie 
- 15117
nin 
- 15110
ning 
- 15109
niu 
- 14941
nong 
- 14937
nu 
- 14933
nv 
- 14930
nuan 
- 14929
nue 
- 14928
nuo 
- 14926
- 14922
ou 
- 14921
pa 
- 14914
pai 
- 14908
pan 
- 14902
pang 
- 14894
pao 
- 14889
pei 
- 14882
pen 
- 14873
peng 
- 14871
pi   - 14857
pian 
- 14678
piao 
- 14674
pie 
- 14670
pin 
- 14668
ping 
- 14663
po 
- 14654
pu 
- 14645
qi 
- 14630
qia 
- 14594
qian 
- 14429
qiang 
- 14407
qiao 
- 14399
qie 
- 14384
qin 
- 14379
qing 
- 14368
qiong 
- 14355
qiu 
- 14353
qu 
- 14345
quan 
- 14170
que 
- 14159
qun 
- 14151
ran 
- 14149
rang 
- 14145
rao 
- 14140
re 
- 14137
ren 
- 14135
reng 
- 14125
ri 
- 14123
rong 
- 14122
rou 
- 14112
ru 
- 14109
ruan 
- 14099
rui 
- 14097
run 
- 14094
ruo 
- 14092
sa 
- 14090
sai 
- 14087
san 
- 14083
sang 
- 13917
sao 
- 13914
se 
- 13910
sen 
- 13907
seng 
- 13906
sha 
- 13905
shai 
- 13896
shan 
- 13894
shang 
- 13878
shao 
- 13870
she 
- 13859
shen 
- 13847
sheng 
- 13831
shi 
- 13658
shou 
- 13611
shu 
- 13601
shua 
- 13406
shuai 
- 13404
shuan 
- 13400
shuang 
- 13398
shui 
- 13395
shun 
- 13391
shuo 
- 13387
si 
- 13383
song 
- 13367
sou 
- 13359
su 
- 13356
suan 
- 13343
sui 
- 13340
sun 
- 13329
suo 
- 13326
ta 
- 13318
tai 
- 13147
tan   - 13138
tang 
- 13120
tao 
- 13107
te 
- 13096
teng 
- 13095
ti 
- 13091
tian 
- 13076
tiao 
- 13068
tie 
- 13063
ting 
- 13060
tong 
- 12888
tou 
- 12875
tu 
- 12871
tuan 
- 12860
tui 
- 12858
tun 
- 12852
tuo 
- 12849
wa 
- 12838
wai 
- 12831
wan 
- 12829
wang 
- 12812
wei 
- 12802
wen 
- 12607
weng 
- 12597
wo 
- 12594
wu 
- 12585
xi 
- 12556
xia 
- 12359
xian 
- 12346
xiang 
- 12320
xiao 
- 12300
xie 
- 12120
xin 
- 12099
xing 
- 12089
xiong 
- 12074
xiu 
- 12067
xu 
- 12058
xuan 
- 12039
xue 
- 11867
xun 
- 11861
ya 
- 11847
yan 
- 11831
yang 
- 11798
yao 
- 11781
ye 
- 11604
yi 
- 11589
yin 
- 11536
ying 
- 11358
yo 
- 11340
yong 
- 11339
you 
- 11324
yu 
- 11303
yuan 
- 11097
yue 
- 11077
yun 
- 11067
za 
- 11055
zai 
- 11052
zan 
- 11045
zang 
- 11041
zao 
- 11038
ze 
- 11024
zei 
- 11020
zen 
- 11019
zeng 
- 11018
zha 
- 11014
zhai 
- 10838
zhan 
- 10832
zhang 
- 10815
zhao 
- 10800
zhe 
- 10790
zhen 
- 10780
zheng 
- 10764
zhi 
- 10587
zhong 
- 10544
zhou 
- 10533
zhu 
- 10519
zhua 
- 10331
zhuai 
- 10329
zhuan 
- 10328
zhuang 
- 10322
zhui 
- 10315
zhun 
- 10309
zhuo 
- 10307
zi 
- 10296
zong 
- 10281
zou 
- 10274
zu 
- 10270
zuan 
- 10262
zui 
- 10260
zun 
- 10256
zuo 
- 10254

 


 

posted @ 2011-01-26 19:29 暮夏 阅读( ...) 评论( ...) 编辑 收藏
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值