当前位置:范文大全 > 调查报告 > 语法分析实验心得_语法分析实验报告(实验二)

语法分析实验心得_语法分析实验报告(实验二)

时间:2021-10-21 10:19:46 浏览次数:

  . . . .

 . . ..

 编译原理语法分析实验报告

 软工082班

 兰洁

 4

 实验容

 实验目的实验要求

 程序流程图

 主函数;

 scanner();

 irparser()函数

 yucu() /*语句串分析*/

 statement()/*语句分析函数*/

 expression()/*表达式分析函数*/

 term()/*项分析函数*/

 factor()/*因子分析函数*/

 程序代码

 测试用例

 输出结果

 实验心得

 一、实验容:

 编写为一上下文无关文法构造其递归下降语法分析程序,并对任给的一个输入串进行语法分析检查。程序要求能对输入串进行递归下降语法分析,能判别程序是否符合已知的语法规则,如果不符合(编译出错),则输出错误信息。

 二、实验目的:

 构造文法的语法分析程序,要求采用递归下降语法分析方法对输入的字符串进行语法分析,实现对词法分析程序所提供的单词序列的语法检查和结构分析,进一步掌握递归下降的语法分析方法。

 三、实验要求:

 利用C语言编制递归下降分析程序,并对Training语言进行语法分析。

 待分析的Training语言语法。

 用扩充的表示如下:

 <程序>-->function<语句串>endfunc

 <语句串>--><语句>{;<语句>}

 <语句>?<赋值语句>

 <赋值语句>?ID?<表达式>

 <表达式>?<项>{+<项>|-<项>}

 <项>?<因子>{*<因子>|/<因子>}

 <因子>?ID|NUM|(<表达式>)

 备注:实验当中 我对程序进行了扩展,增加了程序识别if条件判断语句,while循环语句的功能

 实验要求说明

 输入单词串以“#”结束,如果是文确的句子,则输出成功信息,打印“success”,否则输出“error”。

 四、程序流程图

 主函数:

 Scanner()函数:

 irparser()函数

 yucu() /*语句串分析*/

 statement()/*语句分析函数*/

 expression()/*表达式分析函数*/

 term()/*项分析函数*/

 factor()/*因子分析函数*/

 五、程序代码:

 递归下降分析文法:

 <程序>-->function< 语句串 >endfunc

 <语句串>--><语句>{ ;<语句> }

 <语句>à<赋值语句> |<if条件语句> | <while循环语句>

 <赋值语句>à <表达式>

 <表达式>à<项>{ +<项> | -<项> }

 <项>à<因子>{*<因子>|/<因子>}

 <因子>àID | NUM | (<表达式>)

 <if条件语句>?(<表达式>)| (ID) |(NUM)?<语句>

 <while条件循环语句>?(<表达式>)| (ID) |(NUM)?<语句>

 备注:红色字体部分为我对代码实现功能的主要修改与扩展部分。

 /*语法分析源代码*/

 #include<stdio.h>

 #include<string.h>

 char prog[80],token[8];

 char ch;

 int syn,p,m=0,n,sum,kk=0;

 char *rwtab[6]={"function","if","then","while","do","endfunc"};

 void yucu();

 void expression();

 void statement();

 void factor();

 void term();

 void irparser();

 void scaner()

 { for (n=0;n<8;n++)

  token[n]=NULL;

  while(ch==' ' || ch=='\n')

  ch=prog[p++];

  m=0;

  if((ch<='z' && ch>='a') || (ch<='Z' && ch>='A'))

  {while((ch<='z' && ch>='a') || (ch<='Z' && ch>='A') || (ch<='9' && ch>='0'))

  {token[m++]=ch;

  ch=prog[p++];

  }

  syn=10;

  for(n=0;n<6;n++)

  if(strcmp(token,rwtab[n])==0)

  { syn=n+1;

  break;

  }

  token[m++]='\0';}

  else

  if(ch<='9' && ch>='0')

  { sum=0;

  while(ch<='9' && ch>='0')

  { sum=sum*10+ch-'0';

  ch=prog[p++];

  }

  syn=11;

  }

  else

  { switch(ch)

  { case'<':m=0;token[m++]=ch;

  ch=prog[p++];

  if(ch=='=')

  {syn=22;

  token[m+1]=ch;}

  else

  {syn=20;ch=prog[--p];}

  break;

  case'>':m=0;token[m++]=ch;

  ch=prog[p++];

  if(ch=='=')

  { syn=24;

  token[m++]=ch;

  }

  else

  {syn=23;p--;

  }

  break;

  case'=' :m= 0;token[m ++ ]=ch;

  ch=prog[p++];

  if(ch=='=')

  { syn= 25;

  token[m++]= ch;

  }

  else

  {syn=18;

  ch=prog[--p];

  }

  break;

  case'!':m=0; token[m++]= ch;

  ch=prog[++p];

  if(ch=='=')

  { syn=22;

  token[m++]= ch;

  }

  else

  syn=-1;

  break;

  case'+':syn=13; token[0]=ch;break;

  case'-':syn=14; token[0]=ch;break;

  case'*':syn=15; token[0]=ch;break;

  case'/':syn=16; token[0]=ch;break;

  case';':syn=26; token[0]=ch;break;

  case'(':syn=27; token[0]=ch;break;

  case')':syn=28; token[0]=ch;break;

  case'#':syn=0; token[0]=ch;break;

  default:syn=-1;//break;

  }

  ch=prog[p++];

  } }

 void irparser()

 { if(syn==1)

  { scaner();

  yucu();/*语句串分析*/

  if(syn==6) /*读到endfunc*/

  { scaner();

  if(syn==0&&kk==0)/*程序分析识别完*/

  printf("success");

  }

  else

  { if(kk!=1) /*没以endfunc结束*/

  { printf("error!need 'endfunc'");

  kk=1;

  }

  }

  }

  else

  { printf("error!need'function'");

  kk=1;

  }

 }

 void yucu() /*语句串分析*/

 { statement();/*调用语句分析函数*/

  while(syn==26)/*一个语句识别结束,继续识别*/

  { scaner();

  statement();

  }

  return;

 }

 void statement()/*语句分析函数*/

 { if(syn==10)

  { scaner();

  if(syn==18) //如果是赋值语句

  { scaner();

  expression();

  } //这个过程实现语法分析判断语句

  else

  { printf("error!evaluate tag error");

  kk=1;

  }

  }

  else

  if(syn==6)

  return;

  else

  if(syn==2) //如果是条件判断语句 就判断条件表达式的语法!

  { scaner();

  if(syn==27) //判断括号匹配

  {do

  {scaner(); //进入括号部进行表达式分析

  expression();

  }while(syn!=28);

  }

  else { printf("error! need another')'");

  kk=1;

  } //()判断完成 !

  scaner(); //然后进行语句块分析!

  statement();

  } //到这里是实现判断if语句的语法分析

 // 类似的往里添加 循环语句!

  else

  if(syn==4) //如果是循环语句 就判断条件表达式的语法!

  { scaner();//ch=prog[p++];

  if(syn==27)

  { do

  {scaner();

  expression();

  }while(syn!=28);

  }

  else {

  printf("error! need another')'");

  kk=1; } //()判断完成 !

  scaner(); //然后进行语句块分析!

  statement();

  } //这里是实现判断while语句的语法分析

  else

  { printf("error!the statement error!");

  kk=1;

  }

 }

 void expression()/*表达式分析函数*/

 { term();

  while(syn==13||syn==14)

  { scaner();

  term(); }

  return;

 }

 void term()/*项分析函数*/

 { factor();

  while(syn==15||syn==16)

  { scaner();

  factor();}

  return;

 }

 void factor()/*因子分析函数*/

 { if(syn==10||syn==11)

  { scaner(); }

  else/*看是否是表达式*/

  { expression();

  if(syn==27)

  { scaner();

  expression();

  if(syn==28)

  { scaner();}

  else

  { printf("error! need another')'");

  kk=1;

  }

  }

  else

  { printf("error! expression error!");

  }

  }

 }

 void main()

 { p=0;

  printf("\n please input the string:\n");

  do

  { ch=getchar();

  prog[p++]=ch;

  } while(ch!='#');

  p=0;

  ch=prog[p++];

  scaner();

  irparser();

 }

 六、测试用例

 测试用例1

 输出结果

 测试用例2

 输出结果

 测试用例3

 输出结果

 function

 a=1;

 b=2;

 c=a+b;

 endfunc

 #

 success

 function

 if(3>1)

 a=1;

 endfunc

 #

 success

 function

 if(a>b)

 a=1;

 while(a>1)

 b=1;

 endfunc

 #

 success

 测试用例4

 a=1

 endfunc

 #

 输出结果

 error!need'function'Press any key to continue

 七、输出结果

 测试用例1

 测试用例2

 测试用例4

 测试用例3

 八、实验心得

 通过编译原理实验二语法分析实验,使得自己对语法分析的流程有了更深刻的了解,使得语法分析递归向下思想更加具体化,虽然源代码并非由自己设计,但是在调试程序的过程中,逐步理解程序递归下降思想,思路不断理清,不仅理解了程序分析赋值语句的算法,同时在这基础上,我对程序做了功能扩展,增加了语法分析条件判断语句和while条件循环语句,即是程序中红色字体部分。在调试与算法功能扩展的过程中,理清了语法分析程序的思路。从一开始对程序的陌生,到后来逐步了解程序的流程,当我耐心的一步一步理解程序思想,一次次的更改测试用例,一遍遍的调试,最终终于得到了预期的答案。这次实验使我对理论的语法分析递归下降的理解更加具体清晰,受益匪浅。