作业5 词法分析程序的设计与实现
词法分析程序(Lexical Analyzer)要求:
- 从左至右扫描构成源程序的字符流
- 识别出有词法意义的单词(Lexemes)
- 返回单词记录(单词类别,单词本身)
- 滤掉空格
- 跳过注释
- 发现词法错误
程序结构:
输入:字符流(什么输入方式,什么数据结构保存)
处理:
–遍历(什么遍历方式)
–词法规则
输出:单词流(什么输出形式)
–二元组
单词类别:
1.标识符(10)
2.无符号数(11)
3.保留字(一词一码)
4.运算符(一词一码)
5.界符(一词一码)
|
单词符号 |
种别码 |
单词符号 |
种别码 |
|
begin |
1 |
: |
17 |
|
if |
2 |
:= |
18 |
|
then |
3 |
< |
20 |
|
while |
4 |
<= |
21 |
|
do |
5 |
<> |
22 |
|
end |
6 |
> |
23 |
|
l(l|d)* |
10 |
>= |
24 |
|
dd* |
11 |
= |
25 |
|
+ |
13 |
; |
26 |
|
- |
14 |
( |
27 |
|
* |
15 |
) |
28 |
|
/ |
16 |
# |
0 |
源代码如下:
1 #include<stdio.h> 2 #include<string.h> 3 #include<stdlib.h> 4 char prog[80],word[8],ch; 5 char *tag[6]={"begin","if","then","while","do","end"}; 6 int syn,i,j,p,sum,row,y; 7 8 void getsyn(){ 9 for(i=0;i<8;i++) 10 word[i]=NULL; 11 ch=prog[p++]; 12 while(ch==' '){ 13 ch=prog[p]; 14 p++; 15 } 16 //标识符 17 if((ch>='a'&&ch<='z')||(ch>='A'&&ch<='Z')){ 18 j=0; 19 while((ch>='0'&&ch<='9')||(ch>='a'&&ch<='z')||(ch>='A'&&ch<='Z')){ 20 word[j++]=ch; 21 ch=prog[p++]; 22 } 23 word[j++]='\0'; 24 p--; 25 syn=10; 26 for(i=0;i<6;i++){ 27 if(strcmp(tag[i],word)==0){ 28 syn=i+1; 29 break; 30 } 31 } 32 } 33 //数字 34 else if(ch>='0'&&ch<='9'){ 35 sum=0; 36 while(ch>='0'&&ch<='9'){ 37 sum=sum*10+(ch-'0'); 38 ch=prog[p++]; 39 } 40 p--; 41 syn=11; 42 } 43 //符号 44 else switch(ch){ 45 case ':':i=0;word[i++]=ch; 46 ch=prog[p++]; 47 if(ch=='='){ 48 word[i++]=ch; 49 syn=18; 50 }else{ 51 syn=17; 52 p--; 53 } 54 break; 55 case '<': 56 i=0; 57 word[i++]=ch; 58 ch=prog[p++]; 59 if(ch=='='){ 60 word[i++]=ch; 61 syn=21; 62 }else if(ch=='>'){ 63 word[i++]=ch; 64 syn=22; 65 }else{ 66 syn=20; 67 p--; 68 } 69 break; 70 case '>': 71 i=0; 72 word[i++]=ch; 73 ch=prog[p++]; 74 if(ch=='='){ 75 word[i++]=ch; 76 syn=24; 77 }else{ 78 syn=23; 79 p--; 80 } 81 break; 82 case '+':word[0]=ch;syn=13;break; 83 case '-':word[0]=ch;syn=14;break; 84 case '*':word[0]=ch;syn=15;break; 85 //case '/':word[0]=ch;syn=16;break; 86 case '=':word[0]=ch;syn=25;break; 87 case ';':word[0]=ch;syn=26;break; 88 case '(':word[0]=ch;syn=27;break; 89 case ')':word[0]=ch;syn=28;break; 90 case '#':word[0]=ch;syn=0;break; 91 case '\n':syn=233;break; 92 //注释 93 case '/': 94 i=0; 95 word[i++]=ch; 96 ch=prog[p++]; 97 if(ch=='/'){ 98 do{ 99 p++; 100 }while(prog[p]!='\n'); 101 if(prog[p]=='\n'){ 102 syn=233;break; 103 } 104 } 105 106 if(ch=='*'){ 107 do{ 108 p++; 109 if(p==y-1 ){ 110 syn=-1;break; 111 } 112 }while(prog[p]=='*'&&prog[p+1]!='/'||prog[p]!='*'&&prog[p+1]=='/'||prog[p]!='*'&&prog[p+1]!='/'); 113 if(prog[p]=='*'&&prog[p+1]=='/'){ 114 p++;p++; 115 syn=233; 116 break; 117 } 118 } 119 120 else{ 121 p--;ch=word[i];syn=16;break; 122 } 123 break; 124 125 default:syn=-1;break; 126 } 127 } 128 129 int main(){ 130 p=0; 131 row=1; 132 printf("请输入语句段:"); 133 do{ 134 ch=getchar(); 135 prog[p++]=ch; 136 }while(ch!='#'); 137 y=p; 138 p=0; 139 do{ 140 getsyn(); 141 switch(syn){ 142 case -1:printf("在第%d行有错误!\n",row);break; 143 case 233:row+=1;break; 144 case 11:printf("(%d,%d)\n",sum,syn);break; 145 default:printf("(%s,%d)\n",word,syn);break; 146 } 147 }while(syn!=0); 148 }
运行结果:

浙公网安备 33010602011771号