wangchao.org
设为首页 | 添加收藏
 
购物视频论坛博客自然风光美女图片王朝网络小游戏BT下载生活百科编程设计软件下载小说
 
化妆 | 音乐 | 影视 | 图书 | 英语 | 宠物 | 美食 | 旅游 | 养生 | 手机 | 数码 | 汽车 | 珠宝 | 美容 | 装修 | 厨房 | 科普 | 动物 | 植物 | 影音 | 百科 | 知道 | 词典
  
 
 您好! 您现在位于: 王朝网络 → 编程设计 → 《中文TTS 的简单实现(基于linux)之 实现语音合成返回上一页 
 
1楼 

中文TTS 的简单实现(基于linux)之 实现语音合成

 
 
  网上购物、在线购物、购物搜索 欢迎光临本站购买图书、影视、音乐、数码、百货,手机等商品。

  合成语音归根到底是根据汉字在字符集的定位来取语音库中的数据
  定位方法:
  根据救字的两个字节中的值.从高字节算出汉字的位wm.从低字节算出汉字的区qm,
  (qm一176)*94+wm一160就是该况字在汉字集里的位置position,
  而该汉字所对应的语音数据的偏移量就是(position一1) 3200+46。
  根据定位方法取得汉字在语音库中的发音数据后,根据WAV格式合成语音文件。
  定位和合成代码如下:
  #define MAXLEN 32000
  /*
  参数str:为纯汉字的字符串,且编码格式为GBK
  返回值:
  -1:表示语音库文件打开错误
  -2:表示合成语音文件 打开/生成错误
  其它:函数执行成功
  */
  int wav(char *str)
  {
  FILE * fpf,*fpt; //文件指针
  int qm,wm; //汉字区、位码
  int re; //函数返回值
  long fileleng=0; //文件长度 后面修改WAV格式时有用
  if((fpf=fopen("ddd.wav","rb+"))==NULL) //打开语音库文件
   return -1;
  if((fpt=fopen("china.wav","wb+"))==NULL) //打开或生成合成后的语音文件,用来播放的
   return -2;
  char head[46]; //WAV 文件头
  char buffer[MAXLEN]; //发音数据BUFF
  memset(buffer,0,MAXLEN); //置0
  fread(head,sizeof(head),1,fpf); //读语音库文件头
  fwrite(head,sizeof(head),1,fpt); //写入合成语音文件
  int l=strlen(str);
  char *s=str;
  for(int i=0;i<=l;i=i+2)
  {
   qm=(unsigned char)*(s+i); //取汉字的区码
   wm=(unsigned char)*(s+1+i); //取汉字的位码
   if (qm<176||qm>215) //判断是否在汉字字符集中
   continue;
  
   if (wm<161||wm>254) //判断是否在汉字字符集中
   continue;
  
   int position =(qm-176)*94+wm-160;
   int offset=(position-1)*MAXLEN+46; //定位
   fseek(fpf,offset,0);
   fread(buffer,sizeof(buffer),1,fpf); //取发音数据
   fwrite(buffer,sizeof(buffer),1,fpt); //写入合成文件
   fileleng++; //合成文件长度增加
  
  } //end for
  re =fileleng;
  fileleng=fileleng*MAXLEN;
  fseek(fpt,42,SEEK_SET);
  fwrite(&fileleng,sizeof(long),1,fpt); //修改合成文件的WAV格式,主要是修改文件大小,具体请看WAV格式表
  fileleng+=44;
  fseek(fpt,4,SEEK_SET);
  fwrite(&fileleng,sizeof(long),1,fpt); //修改合成文件的WAV格式,主要是修改文件大小,具体请看WAV格式表
  fclose(fpf); //关闭文件
  fclose(fpt);
  return re;
  }
  其它:
  由函数WAV可以看出,我们接收用户的输入字符的编码必须为GBK编码,
  所以如果系统使用的不是 GBK编码的话,我们还应当进行编码转换。
  如果编码正确的话,还得从把用户的输入中把中文字符给提取出来。
  为此,我写了小段代码,用来过滤非中文字符的。
  void trans(char *str)
  {
  int i = 0, j = 0;
  while( str[i] != '\0' )
  {
   if ( str[i] < 0 )
   {
   str[j++] = str[i++];
   str[j++] = str[i++];
   }
   else
   i++;
  } //end while
  str[j] = '\0';
  }
  
  文章导读:
  中文TTS 的简单实现(基于linux)之 前言
http://blog.csdn.net/dedodong/archive/2006/07/15/923543.aspx
  中文TTS 的简单实现(基于linux)之 实现原理:
http://blog.csdn.net/dedodong/archive/2006/07/16/927041.aspx[/url]
  中文TTS 的简单实现(基于linux)之 语音库的实现
  [url=http://blog.csdn.net/dedodong/archive/2006/08/22/1105742.aspx]http://blog.csdn.net/dedodong/archive/2006/08/22/1105742.aspx

  中文TTS 的简单实现(基于linux)之 后记
http://blog.csdn.net/dedodong/archive/2006/08/24/1109908.aspx

合成语音归根到底是根据汉字在字符集的定位来取语音库中的数据 定位方法: 根据救字的两个字节中的值.从高字节算出汉字的位wm.从低字节算出汉字的区qm, (qm一176)*94+wm一160就是该况字在汉字集里的位置position, 而该汉字所对应的语音数据的偏移量就是(position一1) 3200+46。 根据定位方法取得汉字在语音库中的发音数据后,根据WAV格式合成语音文件。 定位和合成代码如下: #define MAXLEN 32000 /* 参数str:为纯汉字的字符串,且编码格式为GBK 返回值: -1:表示语音库文件打开错误 -2:表示合成语音文件 打开/生成错误 其它:函数执行成功 */ int wav(char *str) { FILE * fpf,*fpt; //文件指针 int qm,wm; //汉字区、位码 int re; //函数返回值 long fileleng=0; //文件长度 后面修改WAV格式时有用 if((fpf=fopen("ddd.wav","rb+"))==NULL) //打开语音库文件 return -1; if((fpt=fopen("china.wav","wb+"))==NULL) //打开或生成合成后的语音文件,用来播放的 return -2; char head[46]; //WAV 文件头 char buffer[MAXLEN]; //发音数据BUFF memset(buffer,0,MAXLEN); //置0 fread(head,sizeof(head),1,fpf); //读语音库文件头 fwrite(head,sizeof(head),1,fpt); //写入合成语音文件 int l=strlen(str); char *s=str; for(int i=0;i<=l;i=i+2) { qm=(unsigned char)*(s+i); //取汉字的区码 wm=(unsigned char)*(s+1+i); //取汉字的位码 if (qm<176||qm>215) //判断是否在汉字字符集中 continue; if (wm<161||wm>254) //判断是否在汉字字符集中 continue; int position =(qm-176)*94+wm-160; int offset=(position-1)*MAXLEN+46; //定位 fseek(fpf,offset,0); fread(buffer,sizeof(buffer),1,fpf); //取发音数据 fwrite(buffer,sizeof(buffer),1,fpt); //写入合成文件 fileleng++; //合成文件长度增加 } //end for re =fileleng; fileleng=fileleng*MAXLEN; fseek(fpt,42,SEEK_SET); fwrite(&fileleng,sizeof(long),1,fpt); //修改合成文件的WAV格式,主要是修改文件大小,具体请看WAV格式表 fileleng+=44; fseek(fpt,4,SEEK_SET); fwrite(&fileleng,sizeof(long),1,fpt); //修改合成文件的WAV格式,主要是修改文件大小,具体请看WAV格式表 fclose(fpf); //关闭文件 fclose(fpt); return re; } 其它: 由函数WAV可以看出,我们接收用户的输入字符的编码必须为GBK编码, 所以如果系统使用的不是 GBK编码的话,我们还应当进行编码转换。 如果编码正确的话,还得从把用户的输入中把中文字符给提取出来。 为此,我写了小段代码,用来过滤非中文字符的。 void trans(char *str) { int i = 0, j = 0; while( str[i] != '\0' ) { if ( str[i] < 0 ) { str[j++] = str[i++]; str[j++] = str[i++]; } else i++; } //end while str[j] = '\0'; } 文章导读: 中文TTS 的简单实现(基于linux)之 前言 [url=http://blog.csdn.net/dedodong/archive/2006/07/15/923543.aspx]http://blog.csdn.net/dedodong/archive/2006/07/15/923543.aspx[/url] 中文TTS 的简单实现(基于linux)之 实现原理: [url=http://blog.csdn.net/dedodong/archive/2006/07/16/927041.aspx]http://blog.csdn.net/dedodong/archive/2006/07/16/927041.aspx[/url][url=http://blog.csdn.net/dedodong/archive/2006/08/24/1109908.aspx][/url] 中文TTS 的简单实现(基于linux)之 语音库的实现 [url=http://blog.csdn.net/dedodong/archive/2006/08/22/1105742.aspx]http://blog.csdn.net/dedodong/archive/2006/08/22/1105742.aspx[/url] 中文TTS 的简单实现(基于linux)之 后记 [url=http://blog.csdn.net/dedodong/archive/2006/08/24/1109908.aspx]http://blog.csdn.net/dedodong/archive/2006/08/24/1109908.aspx[/url]

 
标签: linux  TTS  中文  基于  实现  简单  语音合成  
 
您可以将本页贴到其他网站
UBB代码HTML代码
 
 
 
 

 
 
 更多内容
 ·中文TTS 的简单实现(基于linux) ·Apache中预创建Preforking MPM 机 ·自动安装Windows2000系统 ·中文Windows 2000登录安全漏洞
 ·Linux下如何接ADSL一类的宽带猫带 ·在RedHat linux 8.0下完整详尽的 ·中小异构Linux网络故障分析与排除 ·Linux操作系统概述
 ·Linux文件系统 ·黑客行为动机是什么—Linux之父的 ·使用 netfilter/iptables 为 Lin ·LUI-linux集群自动安装工具
 ·win2k运行进程简要说明 ·Windows 2000 Recovery Console  ·浅析linux下脚本拨号上网 ·配置支持SSL的Tomcat
 ·决战微软--访中国Linux之父“袁 ·也谈 Windows VS Linux:只有傻瓜 ·什么是linux?谁是linus? ·更好的安全机制,更少的死机——
 ·Win98平台openssl编译方法和分析 ·玩转Xwindow 终端 ·Windows 2000进程细述. ·关于WIN 9X和SCO OpenServer的双
 
 
 
最新评论  点此查看所有评论
 
 
 
 
发表评论(支持UBB码)


验证码:  
 
 
 
© 2005- 王朝网络 版权所有