編譯原理語法分析
《編譯原理語法分析》由會員分享,可在線閱讀,更多相關(guān)《編譯原理語法分析(30頁珍藏版)》請在裝配圖網(wǎng)上搜索。
1、上機練習(xí)二:語法分析
一、根據(jù)上機練習(xí)一給出的PL/0語言擴充的巴克斯范式語法描述,利用遞歸下降的語法分析方法,編寫PL/0語言的語法分析程序。
要求:
1. 對給出的PL/0語言進行分析,證明其可以進行自上而下的語法分析;
2. 對block、proc、statement、condition、expression、term、factor進行分析,畫出語法分析圖,在此基礎(chǔ)上描述這些子程序的設(shè)計思想;
3. 具有一定的語法錯誤處理能力;
二、源代碼
#include
2、clude
3、 ch = ; string key[15] = { "begin", "end", "if", "then", "else", "while", "write", "read", "do", "call", "const", "var", "procedure", "program", "odd" };//預(yù)設(shè)保留字 void prog(); void block(); void condecl(); void _const(); void vardecl(); void proc(); void body(); void statement(); void
4、lexp(); void exp(); void term(); void factor(); void error0() { cout << "program標(biāo)示符出錯" << endl; exit(0); //出錯即退出 } void error1() { cout << "第" << line << "行缺少分號" << endl; } void error2() { cout << "第" << line << "行標(biāo)識符(變量名)出錯" << endl; } void error3() { cout << "第" << li
5、ne << "常量未聲明(缺少const)" << endl;
}
void error4()
{
cout << "第" << line << "常量未賦值" << endl;
}
void error5()
{
cout << "第" << line << "賦值號出錯或者缺少賦值號" << endl;
}
void error6()
{
cout << "第" < 6、
}
void error8()
{
cout << "第" << line << "行缺少左括號" << endl;
}
void error9()
{
cout << "第" << line << "行缺少參數(shù)" << endl;
}
void error10()
{
cout << "第" << line << "行procedure錯誤" << endl;
}
void error11()
{
cout << "第" << line << "行缺少end(begin與end不匹配)" << endl;
}
void error12()
{
7、
cout << "第" << line << "行缺少then(if與then不匹配)" << endl;
}
void error13()
{
cout << "第" << line << "行缺少do(while與do不匹配)" << endl;
}
void error14()
{
cout << "第" << line << "行調(diào)用過程缺少標(biāo)識符" << endl;
}
void error15()
{
cout << "第" << line << "行缺少分號" << endl;
}
void error16()
{
cout << "第 8、" << line << "行條件語句出錯(缺少界符)" << endl;
}
void prog()//程序的遞歸子程序?qū)崿F(xiàn)
{
line++;
if (yufa0.SYM == "program")// program
{
mm++; yufa0.SYM = yufa2[mm].SYM;
if (yufa0.SYM == "biaoshifu") // 9、.SYM = yufa2[mm].SYM;
block();
}
else error1();//缺少;
}
else error2();//缺少標(biāo)識符或者標(biāo)識符錯誤
}
else error0();
cout << "\n\n--------------------------語法分析結(jié)束------------------------\n\n" << endl;
}
void block()//程序體的遞歸子程序?qū)崿F(xiàn), 10、fa0.SYM == "const")
condecl();
if (yufa0.SYM == "var")
vardecl();
if (yufa0.SYM == "procedure")
proc();
body();
}
void condecl()//常量說明的遞歸子程序?qū)崿F(xiàn), 11、();// 12、
{
if (yufa0.SYM == "biaoshifu") // 13、
}
else error2(); //缺少標(biāo)識符
}
void vardecl()//變量說明的遞歸子程序?qū)崿F(xiàn), 14、m++; yufa0.SYM = yufa2[mm].SYM;//下一單詞
if (yufa0.SYM == "biaoshifu") // 15、);//變量未聲明
}
void proc()// 16、
mm++; yufa0.SYM = yufa2[mm].SYM;
if (yufa0.SYM == "biaoshifu")// 17、 }
else error2();
}
}
if (yufa0.SYM == ")")// )
{
mm++; yufa0.SYM = yufa2[mm].SYM;
if (yufa0.SYM == ";") //;
{
mm++; yufa0.SYM = yufa2[mm].SYM;//下一單詞---------->>
block();
while (yufa0.SYM == ";")
{
mm++; yufa0. 18、SYM = yufa2[mm].SYM;
proc();
}
}
else error1();// 缺少;
}
else error7();//括號不匹配 (右括號少)
}
else error8();//左括號缺少
}
else error9();//缺少參數(shù)
}
else error10();//procedure錯誤
}
void body()//
19、fa0.SYM == "begin") { line++; mm++; yufa0.SYM = yufa2[mm].SYM; statement(); // while ((yufa0.SYM == "biaoshi") || (yufa0.SYM == "if") || (yufa0.SYM == "while") || // (yufa0.SYM == "call") || (yufa0.SYM == "read") || (yufa0.SYM == "write") || (yufa0.SYM == "begin")) // error1();//語
20、句未到最后一條,缺少";"
while(yufa0.SYM == ";")
{
mm++; yufa0.SYM = yufa2[mm].SYM;
statement();
}
if (yufa0.SYM == "end")
{
line ++;
mm++; yufa0.SYM = yufa2[mm].SYM;
}
else error11();//缺少end與begin匹配
}
else error12();//缺少begin
}
//
21、statement> //語句
// |if
22、 if (yufa0.SYM == "biaoshifu") // 23、tement>]
{
line++;
mm++; yufa0.SYM = yufa2[mm].SYM;
lexp();
if (yufa0.SYM == "then")
{
mm++; yufa0.SYM = yufa2[mm].SYM;
statement();
if (yufa0.SYM == "else")
{
mm++; yufa0.SYM = yufa2[mm].SYM;
statement();
}
}
else error12();//缺少then
}
els 24、e if (yufa0.SYM == "while")//while 25、d>[( 26、 exp();
}
if (yufa0.SYM == ")")
{
mm++; yufa0.SYM = yufa2[mm].SYM;
}
else error7();//缺少右括號
}
// 此處不會報錯,[( 27、= yufa2[mm].SYM;
if (yufa0.SYM == "(")
{
mm++; yufa0.SYM = yufa2[mm].SYM;
if (yufa0.SYM == "biaoshifu")
{
mm++; yufa0.SYM = yufa2[mm].SYM;
while (yufa0.SYM == ",")
{
mm++; yufa0.SYM = yufa2[mm].SYM;
if (yufa0.SYM == "biaoshifu")
{
mm++; yu 28、fa0.SYM = yufa2[mm].SYM;
}
else error2();//缺少標(biāo)示符
}
if (yufa0.SYM == ")")
{
mm++; yufa0.SYM = yufa2[mm].SYM;
}
else error7();//缺少右括號
}
else error9();//read缺少參數(shù)
}
else error8();//缺少左括號
}
else if (yufa0.SYM == "write")//write ( 29、exp>})
{
line++;
mm++; yufa0.SYM = yufa2[mm].SYM;
if (yufa0.SYM == "(")
{
mm++; yufa0.SYM = yufa2[mm].SYM;
exp();
while (yufa0.SYM == ",")
{
mm++; yufa0.SYM = yufa2[mm].SYM;
exp();
}
if (yufa0.SYM == ") 30、")
{
mm++; yufa0.SYM = yufa2[mm].SYM;
}
else error7();//缺少右括號
}
else error8();//缺少左括號
}
else body();// 31、> → =|<>|<|<=|>|>=
// 32、= "g") || (yufa0.SYM == "l") || (yufa0.SYM == "ne") || (yufa0.SYM == "l") || (yufa0.SYM == "="))
{
mm++;
yufa0.SYM = yufa2[mm].SYM;
exp();
}
else
error15();//條件語句出錯,缺少界符
}
//odd是否存在?
}
void exp()// 33、ufa0.SYM == "-"))
{
mm++;
yufa0.SYM = yufa2[mm].SYM;
term();// 34、fa0.SYM == "*") || (yufa0.SYM == "/"))// 35、;
yufa0.SYM = yufa2[mm].SYM;
}
else if (yufa0.SYM == "(")
{
mm++;
yufa0.SYM = yufa2[mm].SYM;
exp();
if (yufa0.SYM == ")")
{
mm++;
yufa0.SYM = yufa2[mm].SYM;
}
else error7(); //缺少右括號
}
else error8();//缺少左括號
}
string Concat(char ch,string strToken)
{
s 36、trToken += ch;
return strToken;
}
int IsLetter(char c ) //判斷字母
{
if (((c <= z)&&(c >= a)) || ((c <= Z)&&(c >= A)))
return 1;
else return 0;
}
int IsDigit(char c) //判斷數(shù)字
{
if ((c >= 0)&&(c <= 9))
return 1;
else return 0;
}
int IsKey(string StrToken) // 37、判斷保留字
{
int i;
for (i = 0; i<15; i++)
{
if (key[i].compare(StrToken) == 0)
return 1;
}
return 0;
}
void getsym(fstream &file)
{
string StrToken = "";
// if (ch == || ch == \t || ch == \n) //濾掉空白字符
// ch = file.get();
if (IsLetter(ch))
{
while (IsLetter(c 38、h) || IsDigit(ch))
{
StrToken = Concat(ch,StrToken);
ch = file.get();
}
if (IsKey(StrToken))
{
int i;
for (i = 0; i<15; i++)
{
if (key[i].compare(StrToken) == 0)
yufa1.SYM = key[i];
}
yufa1.strToken = StrToken;
}
else
{
yufa1.SYM 39、= "biaoshifu";
yufa1.strToken = StrToken;
}
}
if (IsDigit(ch))
{
StrToken = "";
while(IsDigit(ch))
{
StrToken = Concat(ch,StrToken);
ch = file.get();
}
if(IsLetter(ch)) //數(shù)字后面跟字母,錯誤詞法
{
while(IsLetter(ch)||IsDigit(ch))
{
St 40、rToken = Concat(ch,StrToken);
ch = file.get();
}
cout <<"詞法錯誤!(數(shù)字后面跟字母) "<< StrToken<< endl;
}
else
yufa1.SYM = "digit";
yufa1.strToken = StrToken;
}
else switch (ch)
{
case+:{yufa1.SYM = "+";yufa1.strToken = "+";ch = file.get();break;}
case-:{yufa1.SYM = "-";yufa1 41、.strToken = "-";ch = file.get();break;}
case*:{yufa1.SYM = "*";yufa1.strToken = "*";ch = file.get();break;}
case/:{yufa1.SYM = "/";yufa1.strToken = "/";ch = file.get();break;}
case(:{yufa1.SYM = "(";yufa1.strToken = "(";ch = file.get();break;}
case):{yufa1.SYM = ")";yufa1.strToken = ")";ch = 42、 file.get();break;}
case=:{yufa1.SYM = "=";yufa1.strToken = "=";ch = file.get();break;}
case;:{yufa1.SYM = ";";yufa1.strToken = ";";ch = file.get();break;}
case,:{yufa1.SYM = ",";yufa1.strToken = ",";ch = file.get();break;}
case::
{
ch = file.get();
if (ch == =)
{
yufa1.SYM = 43、"fuzhi";
yufa1.strToken = ":=";
}
else
cout << ":" << "詞法錯誤(:后面沒有=)" << endl;
ch = file.get();
break;
}
case>:
{
ch = file.get();
if (ch == =)
{
yufa1.SYM = "ge";
yufa1.strToken = ">=";
}
else
{
yufa1.SYM = "g";
yufa1.strToken = ">";
44、}
ch = file.get();
break;
}
case<:
{
ch = file.get();
if (ch == =)
{
yufa1.SYM = "le";
yufa1.strToken = "<=";
}
else if (ch == >)
{
yufa1.SYM = "ne";
yufa1.strToken = "<>";
}
else
{
yufa1.SYM = "l";
yufa1.strToken = "<";
}
45、 ch = file.get();
break;
}
}
}
int main()
{
int nn = 0;
string StrToken = "";
fstream file;
char ch;
int ll;
char filename[30];
cout << "請輸入源文件名:";
cin.getline(filename, 30);
file.open(filename, ios::in);
if (!file)
{
cout << "文件打開失敗!\n\n";
exit(0);
}
yufa 46、2[nn].l = 0;
cout << "\n--------------------------詞法分析------------------------" << endl;
// ch = file.get();
while (!file.eof())
{
// if (ch == || ch == \t || ch == \n) //濾掉空白字符
// ch = file.get();
// ch = file.get();
if (ch == || ch == \t)
ch=file.get();
while ( 47、ch == \n)
{
ll ++;
ch = file.get();
}
getsym(file);
nn++;
yufa2[nn].SYM = yufa1.SYM;
yufa2[nn].strToken = yufa1.strToken;
yufa2[nn].l = ll;
// cout.setf(ios::left);
cout << "(" << setw(2) << nn << ") ";
cout << setw(13) << yufa2[nn].SYM << se 48、tw(9) << yufa2[nn].strToken << "\n";
cout << setw(13) << yufa1.SYM << setw(9) << yufa1.strToken << "\n";
}
// nn++;
// yufa2[nn].SYM = "the_end";//完成
// yufa2[nn].strToken = "the_end";
file.close();
// cout << "\n\n\n--------------------------語法分析------------------------" << endl;
yufa0.SYM = yufa2[mm].SYM;
// yufa0.SYM = yufa1.SYM;
prog();
return 0;
}
- 溫馨提示:
1: 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
2: 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
3.本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
5. 裝配圖網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負責(zé)。
6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請與我們聯(lián)系,我們立即糾正。
7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時也不承擔(dān)用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。
最新文檔
- 汽車制造工藝學(xué)-第1章概述ppt課件
- 中樞神經(jīng)系統(tǒng)磁共振序列應(yīng)用課件
- 高考生物大一輪復(fù)習(xí)-第19課時-遺傳基本定律的知識梳理與題型探究ppt課件-新人教版
- 高中物理15斜拋運動ppt課件粵教版必修
- 七年級地理上冊3.2氣溫和降水(第2課時降水的變化干濕區(qū))ppt課件 中圖版
- (人教版)角的初步認識課件
- 小學(xué)生安全教育之常見的簡單急救課件
- 癲癇專題知識培訓(xùn)ppt課件
- 牛津高中英語高一上課件M2U3Task
- 中小學(xué)英語公開課—《Childhood--Friends》課件
- 高一地理必修一21地球上的大氣人教版課件
- 振蕩器的設(shè)計解析ppt課件
- 誤差理論與數(shù)據(jù)處理 全套課件
- 直腸癌化療醫(yī)療護理查房培訓(xùn)ppt課件
- 模塊五-商務(wù)會面禮儀課件