编程实现英文数字到中文大写数字的转换 分类: 编译原理 2014-06-02 15:15 541人阅读 评论(0) 收藏
本程序实现英文数字到中文大写数字的转换。
主要思想是利用该语法自底向上地构造出1——>999999999999;
然后将数字转换成中文大写。
利用flex进行词法分析,bison进行句法分析。
语法如下:
e1-->one|two|three|four|five|six|seven|eight|nine
e2-->ten|eleven|twelve|thirteen|fourteen|fifteen|sixteen|seventeen|eighteen|nineteen
e3-->twenty|thirty|forty|fifty|sixty|seventy|eighty|ninety
e4-->e3-e1
|e3
|e2
|e1
e51-->e1 hundred and e4
|e1 hundred
e52-->e51
|e4
e61-->e52 thousand e51
|e52 thousand and e4
|e52 thousand
e62-->e61
|e52
e71-->e52 million e61
|e52 million e51
|e52 million and e4
|e52 million
e72-->e71
|e62
e81-->e52 billion e71
|e52 billion e61
|e52 billion e51
|e52 billion and e4
|e52 billion
e82-->e81
|e72
|zero
parser.y文件如下:
程序的运行:
flex lex.l
bison parser.y
g++ parser.tab.c -ly -ll
./a.out
输入英文数字回车得到对应的中文大写。
主要思想是利用该语法自底向上地构造出1——>999999999999;
然后将数字转换成中文大写。
利用flex进行词法分析,bison进行句法分析。
语法如下:
e1-->one|two|three|four|five|six|seven|eight|nine
e2-->ten|eleven|twelve|thirteen|fourteen|fifteen|sixteen|seventeen|eighteen|nineteen
e3-->twenty|thirty|forty|fifty|sixty|seventy|eighty|ninety
e4-->e3-e1
|e3
|e2
|e1
e51-->e1 hundred and e4
|e1 hundred
e52-->e51
|e4
e61-->e52 thousand e51
|e52 thousand and e4
|e52 thousand
e62-->e61
|e52
e71-->e52 million e61
|e52 million e51
|e52 million and e4
|e52 million
e72-->e71
|e62
e81-->e52 billion e71
|e52 billion e61
|e52 billion e51
|e52 billion and e4
|e52 billion
e82-->e81
|e72
|zero
lex.l文件如下:
%% zero {yylval=0;return ZERO;} one {yylval=1;return NUM1;} two {yylval=2;return NUM1;} three {yylval=3;return NUM1;} four {yylval=4;return NUM1;} five {yylval=5;return NUM1;} six {yylval=6;return NUM1;} seven {yylval=7;return NUM1;} eight {yylval=8;return NUM1;} nine {yylval=9;return NUM1;} ten {yylval=10;return NUM2;} eleven {yylval=11;return NUM2;} twelve {yylval=12;return NUM2;} thirteen {yylval=13;return NUM2;} fourteen {yylval=14;return NUM2;} fifteen {yylval=15;return NUM2;} sixteen {yylval=16;return NUM2;} seventeen {yylval=17;return NUM2;} eighteen {yylval=18;return NUM2;} nineteen {yylval=19;return NUM2;} twenty {yylval=20;return NUM3;} thirty {yylval=30;return NUM3;} forty {yylval=40;return NUM3;} fifty {yylval=50;return NUM3;} sixty {yylval=60;return NUM3;} seventy {yylval=70;return NUM3;} eighty {yylval=80;return NUM3;} ninety {yylval=90;return NUM3;} hundred {return HUNDRED;} thousand {return THOUSAND;} million {return MILLION;} billion {return BILLION;} and {return AND;} [ \t]+ /* skip blanks */ .|\n { return yytext[0];}
parser.y文件如下:
%{ #include<cmath> #include <string> #include <iostream> using namespace std; void yyerror(string msg); string trans(int term); void dtos(long term,string &result); int yylex(); #define YYSTYPE long %} %token NUM1 %token NUM2 %token NUM3 %token ZERO %token HUNDRED %token THOUSAND %token MILLION %token BILLION %token AND %% lines : lines e82 '\n' {string result;dtos($2,result);cout<<result<<endl;} | lines '\n' | /*empty*/ |error '\n' {yyerrok;} ; e82:e81 {$$=$1;} |e72 {$$=$1;} |ZERO {$$=0;} ; e81:e52 BILLION e71 {$$=$1*pow(10,9)+$3;} |e52 BILLION e61 {$$=$1*pow(10,9)+$3;} |e52 BILLION e51 {$$=$1*pow(10,9)+$3;} |e52 BILLION AND e4 {$$=$1*pow(10,9)+$4;} |e52 BILLION {$$=$1*pow(10,9);} ; e72:e71 {$$=$1;} |e62 {$$=$1;} ; e71:e52 MILLION e61 {$$=$1*pow(10,6)+$3;} |e52 MILLION e51 {$$=$1*pow(10,6)+$3;} |e52 MILLION AND e4 {$$=$1*pow(10,6)+$4;} |e52 MILLION {$$=$1*pow(10,6);} ; e62:e61 {$$=$1;} |e52 {$$=$1;} ; e61:e52 THOUSAND e51 {$$=$1*pow(10,3)+$3;} |e52 THOUSAND AND e4 {$$=$1*pow(10,3)+$4;} |e52 THOUSAND {$$=$1*pow(10,3);} ; e52:e51 {$$=$1;} |e4 {$$=$1;} ; e51:e1 HUNDRED AND e4 {$$=$1*pow(10,2)+$4;} |e1 HUNDRED {$$=$1*pow(10,2);} ; e4:e3'-'e1{$$=$1+$3;} |e3 {$$=$1;} |e2 {$$=$1;} |e1 {$$=$1;} ; e3:NUM3 {$$=$1;} ; e2:NUM2 {$$=$1;} ; e1:NUM1 {$$=$1;} ; %% #include "lex.yy.c" int main() { return yyparse(); } void yyerror(string msg) { cout<<msg<<endl; } string trans(int term) { if(term==1) return "壹"; if(term==2) return "贰"; if(term==3) return "叁"; if(term==4) return "肆"; if(term==5) return "伍"; if(term==6) return "陆"; if(term==7) return "柒"; if(term==8) return "捌"; if(term==9) return "玖"; } void dtos(long term,string &result) { bool flag1=false,flag2=false,flag3=false,flag4=false; long temp1=term/100000000; if(temp1!=0) { flag1=true; dtos(temp1,result); result+="亿"; } term%=100000000; long temp2=term/10000; if(temp2!=0) { if(temp2<1000) { if(flag1) result+="零"; } flag2=true; dtos(temp2,result); result+="万"; } else if(flag1) { result+="零";} term%=10000; long temp3=term/1000; if(temp3!=0) { flag3=true; result+=trans(temp3); result+="仟"; } else if(flag2) {result+="零";} term%=1000; long temp4=term/100; if(temp4!=0) { flag4=true; result+=trans(temp4); result+="佰"; } else if(flag3) {result+="零";} term%=100; long temp5=term/10; if(temp5!=0) { result+=trans(temp5); result+="拾"; } else if(flag4) {result+="零";} term%=10; long temp6=term; if(temp6!=0) result+=trans(temp6); if(result=="") result+="零"; string temp=result.substr(result.length()-3,result.length()); if((result!="零")&&(temp=="零")) { result=result.substr(0,result.length()-3); } }
程序的运行:
flex lex.l
bison parser.y
g++ parser.tab.c -ly -ll
./a.out
输入英文数字回车得到对应的中文大写。
版权声明:本文为博主原创文章,未经博主允许不得转载。