详细代码请见同名文件
Enhance the understanding of parser by implementing PDA.
1)Input
Stream of characters
CFG(Combination of CFGs of some classes of sentences)
2)Output
Sequence of derivations if top-down syntax analyzing methods are used.
Sequence of reductions if bottom-up syntax analyzing methods are used.
3)Classes of sentences are defined by yourself
4)Error handling may be included
What is the things should be done to construct a PARSER:
Construct a LL (1) table。
Get the Token continuously from the Analyzer constructed in the Project 1.
Match the token got with the head of the stack. If it matches, get the next token, else, refer to the table to find a production till there are no productions to choose.
我在网上找到了一个C语言语法子集:
<程序> → <语句><程序> | Ɛ;
<语句> → <变量定义语句> | <赋值语句> | <函数调用语句> |
<变量定义语句> → <变量类型><标识符表>;
<赋值语句> → <标识符> = <表达式>;
<函数调用语句> → <标识符> ( <标识符表> );
<循环语句> → while ( <条件表达式> ) { <语句> }
<标识符表> → <标识符>| <标识符表>,<标识符>
<条件表达式> → <表达式><比较运算符><表达式>
<比较运算符> → > | >= | < | <= | != | ==
<变量类型>→ char | short | int | long | float | double
<表达式> → +T | -T | T | <表达式> + T | <表达式>-T
T → F | T*F | T/F
F → <标识符> | <无符号整数> | (<表达式 >)
将中文描述用英文非终结符替换,替换如下:
S' →程序
S →语句
Q →else语句
L →标识符表
E →表达式
X →条件表达式
R →比较运算符
id →标识符
num→常量
替换结果文法产生式为:
S' → S S'| Ɛ
S → A L; | id=E; | id(L); | if(X){S}Q | while(X){S} | Ɛ
A → char | short | int | long | float | double
Q → else{S} | Ɛ
L → id | L , id
X → ERE
R → > | >= | < | <= | == | !=
E → +T | -T | T | E+T | E-T
T → F | T*F | T/F
F → id | num | (E)
Cause that LL (1) recursive descent method is used, the left recursion should be eliminated and the common left factor extracted.
S’ → S S’| Ɛ
S → A L; | id B | if(X){S}Q | while(X){S} | Ɛ
A → char | short | int | long | float | double
B → (L); | =E;
L → id | L , id
Q → else{S} | Ɛ
X → ERE
R → > | >= | < | <= | == | !=
E → +T | -T | T | EM
M → +T | -T
T → F | TN
N → *F |/F
F → id | num | (E)
S’ → S S’
S’ → Ɛ
S → A L;
S → id B
S → if(X){S}Q
S → while(X){S}
S → Ɛ
B → (L);
B → =E;
L → id L’
L’→ , id L’
L’→ Ɛ
Q → else{S}
Q → Ɛ
X → ERE
E → TE’
E → +TE’
E → -TE’
E’ → ME’
E’ → Ɛ
M → +T
M → -T
T → FT’
T’ → NT’
T’ → Ɛ
N → *F
N → /F
F → id
F → num
F → (E)
R → >
R → >=
R → <
R → <=
R → ==
R → !=
A → char
A → short
A → int
A → long
A → float
A → double
First(S’)={ char , short , int , long , float , double , id , if , while , Ɛ }
First(S)={ char , short , int , long , float , double , id , if , while , Ɛ }
First(A)={ char , short , int , long , float , double }
First(B)={ ( , = }
First(L)={ id }
First(L’)={ ,, Ɛ }
First(Q)={ else , Ɛ }
First(X)={ + , - , id , num , ( }
First(R)={ > , >= , < , <= , != , == }
First(E)={ + , - , id , num , ( }
First(E’)={ + , - , Ɛ }
First(M)={ + , - }
First(T)={ id , num , ( }
First(T’)={ * , / , Ɛ }
First(N)={ * , / }
First(F)={ id , num , ( }
Follow (S’)={ $ }
Follow (S)={ $ , } }
Follow (B)={ $ , } }
Follow (L)={ $ , ) , ; , } }
Follow (L’)={ $ , ) , ; , } }
Follow (Q)={ $ , } }
Follow (X)={ ) }
Follow (R)={ + , - , id , num , ( }
Follow (E)={ ) , ; , > , >= , < , <= , != , == }
Follow (E’)={ ) , ; , > , >= , < , <= , != , == }
Follow (M)={ ) , ; , > , >= , < , <= , != , == , + , - }
Follow (T)={ ) , ; , > , >= , < , <= , != , == , + , - }
Follow (T’)={ ) , ; , > , >= , < , <= , != , == , + , - }
Follow (N)={ ) , ; , > , >= , < , <= , != , == , + , - , * , / }
Follow (F)={ ) , ; , > , >= , < , <= , != , == , + , - , * , / }
LL(1) 预测分析表中的数字分别代表的产生式如下:
0:S → A L;
1:S → id B
2:S → if(X){P}Q
3:S → while(X){P}
4:S → Ɛ
5:B → (L);
6:B → =E;
7:L → id L’
8:L’→ ,id L’
9:L’→ Ɛ
10:Q → else{S}
11:Q → Ɛ
12:X → ERE
13:E → +TE’
14:E → -TE’
15:E → TE’
16:E’→ ME’
17:E’→ Ɛ
18:M → +T
19:M → -T
20:T → FT’
21:T’→ NT’
22:T’→ Ɛ
23:N → *F
24:N → /F
25:F → id
26:F → num
27:F → (E)
28:R → >
29:R → >=
30:R → <
31:R → <=
32:R → ==
33:R → !=
34:S’ → S S’
35:S’ → Ɛ
36:A → char
37:A → short
38:A → int
39:A → long
40:A → float
41:A → double
id | num | if | else | while | + | - | * | / | > | >= | < | <= | == | != | ; | , | ( | ) | { | } | = | char | short | int | long | float | double | $ | |
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
S | 1 | 2 | 3 | 4 | 35 | ||||||||||||||||||||||||
S’ | 34 | 34 | 34 | 34 | 34 | 34 | 34 | 34 | 34 | 34 | |||||||||||||||||||
A | 36 | 37 | 38 | 39 | 40 | 41 | |||||||||||||||||||||||
B | 5 | 6 | |||||||||||||||||||||||||||
L | 7 | ||||||||||||||||||||||||||||
C | 9 | 8 | 9 | 9 | 9 | ||||||||||||||||||||||||
Q | 10 | 11 | 11 | ||||||||||||||||||||||||||
X | 12 | 12 | 12 | 12 | 12 | ||||||||||||||||||||||||
E | 15 | 15 | 13 | 14 | 15 | ||||||||||||||||||||||||
D | 16 | 16 | 17 | 17 | 17 | 17 | 17 | 17 | 17 | 17 | |||||||||||||||||||
M | 18 | 19 | |||||||||||||||||||||||||||
T | 20 | 20 | 20 | ||||||||||||||||||||||||||
H | 22 | 22 | 21 | 21 | 22 | 22 | 22 | 22 | 22 | 22 | 22 | 22 | |||||||||||||||||
N | 23 | 24 | |||||||||||||||||||||||||||
F | 25 | 26 | 27 | ||||||||||||||||||||||||||
R | 28 | 29 | 30 | 31 | 32 | 33 |
|---ll1Table() 根据g)中的LL1表通过switch控制流进行状态转移的实现
|---initMap() 将Token编码和符号对应
|---intiProductions() 提供42个产生式,属性包括产生式左侧、产生式右侧、产生式描述
|---executeGra() 实现整个GrammarAnalyzer的程序控制
public void executeGra(String strLex) throws Exception {
int index = 0;
initMap();
initProductions();
readToReader(strLex);//将String字符串转为token的标号存储
stack.push(String.valueOf(mapS2i.get("$")));
stack.push("S'");//此时语法栈为 S'$
List<GraStack> stackItems = new ArrayList<>();
while (!stack.isEmpty()) {
GraStack graStack = new GraStack();
graStack.setNum(++index);
// 读取当前栈
graStack.setCurrStack(getCurrStack());
// 读取待读队列
graStack.setUnread(getUnread());
// 判断是否匹配
if (!match()) {
int i = ll1Table();
if (i >= 0) {
stackPush(productions[i]);
graStack.setCandidate(productions[i].prod);
} else {
//没有Follow集相关的产生式,语法分析错误
throw new Exception("语法分析错误,无匹配的产生式\n当前语法栈为:"+graStack.getCurrStack()+"\n当前字符串为:"+graStack.getUnread());
}
}else {
//若匹配则reader指针向后移位
graStack.setCandidate("move forward");
}
//记录每次ACTION
stackItems.add(graStack);
}
int size=stackItems.size();
for(int i=0;i<size;i++){
GraStack gs=stackItems.get(i);
String result=String.format("%18s %18s",gs.getCurrStack(),gs.getCandidate());
System.out.printf("%d %s %s\n",gs.getNum(),result,gs.getUnread());
}
}
int a;
a=1;
float b;
b=2.0;
if(a<b){
a=b+1;
}else{
b=2;
}
while(a==10){
a=a/1;
}
Result
(3,int)
(20,a)
(49,;)
(20,a)
(31,=)
(30,1)
(49,;)
(5,float)
(20,b)
(49,;)
(20,b)
(31,=)
(30,2.0)
(49,;)
(9,if)
(41,()
(20,a)
(34,<)
(20,b)
(42,))
(45,{)
(20,a)
(31,=)
(20,b)
(37,+)
(30,1)
(49,;)
(46,})
(10,else)
(45,{)
(20,b)
(31,=)
(30,2)
(49,;)
(46,})
(11,while)
(41,()
(20,a)
(32,==)
(30,10)
(42,))
(45,{)
(20,a)
(31,=)
(20,a)
(40,/)
(30,1)
(49,;)
(46,})
------------Start Syntax Analyzing--------------
NUM CURRENT STACK SELECTED PRODUCTION UNREAD STRING
1 S'$ S' → SS' int id ; id = num ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
2 SS'$ S → A L; int id ; id = num ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
3 AL;S'$ A → int int id ; id = num ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
4 intL;S'$ move forward int id ; id = num ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
5 L;S'$ L → id L' id ; id = num ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
6 idL';S'$ move forward id ; id = num ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
7 L';S'$ L' → ε ; id = num ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
8 ;S'$ move forward ; id = num ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
9 S'$ S' → SS' id = num ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
10 SS'$ S → id B id = num ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
11 idBS'$ move forward id = num ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
12 BS'$ B → =E; = num ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
13 =E;S'$ move forward = num ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
14 E;S'$ E → TE' num ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
15 TE';S'$ T → FT' num ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
16 FT'E';S'$ F → num num ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
17 numT'E';S'$ move forward num ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
18 T'E';S'$ T' → ε ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
19 E';S'$ E' → ε ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
20 ;S'$ move forward ; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
21 S'$ S' → SS' float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
22 SS'$ S → A L; float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
23 AL;S'$ A → float float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
24 floatL;S'$ move forward float id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
25 L;S'$ L → id L' id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
26 idL';S'$ move forward id ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
27 L';S'$ L' → ε ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
28 ;S'$ move forward ; id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
29 S'$ S' → SS' id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
30 SS'$ S → id B id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
31 idBS'$ move forward id = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
32 BS'$ B → =E; = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
33 =E;S'$ move forward = num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
34 E;S'$ E → TE' num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
35 TE';S'$ T → FT' num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
36 FT'E';S'$ F → num num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
37 numT'E';S'$ move forward num ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
38 T'E';S'$ T' → ε ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
39 E';S'$ E' → ε ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
40 ;S'$ move forward ; if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
41 S'$ S' → SS' if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
42 SS'$ S → if(X){S}Q if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
43 if(X){S}QS'$ move forward if ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
44 (X){S}QS'$ move forward ( id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
45 X){S}QS'$ X → ERE id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
46 ERE){S}QS'$ E → TE' id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
47 TE'RE){S}QS'$ T → FT' id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
48 FT'E'RE){S}QS'$ F → id id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
49 idT'E'RE){S}QS'$ move forward id < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
50 T'E'RE){S}QS'$ T' → ε < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
51 E'RE){S}QS'$ E' → ε < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
52 RE){S}QS'$ R → < < id ) { id = id + num ; } else { id = num ; } while ( id == num ) { id = id / num ; } $
53
int a;
a=1;
float b;
b=2.0==1;//错误语法
if(a<b){
a=b+1;}
else{
b=2;
}
while(a==10){
a=a/1;
}