递归下降分析程序的设计和实现

递归下降分析程序的设计和实现递归下降分析程序的设计和实现一 实验的目的和要求 1 了解语法分析的主要任务 2 实现基本的递归下降分析器 能够分析任意的符号串是否为该文法所定义的合法算术表达式 二 实验环境 Windows7 Dev C 三 实验准备先将递归下降分析程序的生成认真的学习一遍 理解递归下降分析程序的构成过程 已知文法 G S S aB bD B bC C aS

递归下降分析程序的设计和实现

一、实验的目的和要求
1、了解语法分析的主要任务。 2、实现基本的递归下降分析器,能够分析任意的符号串是否为该文法所定义的合法算术表达式。 
二、实验环境
Windows7 + Dev-C++ 
三、实验准备
先将递归下降分析程序的生成认真的学习一遍,理解递归下降分析程序的构成过程。 已知文法G[S]: S → aB | bD B → bC C → aS | bD | ε D → aB | bD | ε 
  1. 经观察此文法不含左公因式,也不含左递归,求出此文法的FIRST、FOLLOW以及SELECT集。
产生式 FIRST FOLLOW SELECT
S → aB {a} {#} {a}
S → bD {b} {b}
B → bC {b} {#} {b}
C → aS {a} {#} {a}
C → bD {b} {#} {b}
C → ε {ε} {#}
D → aB {a} {#} {a}
D → bD {b} {b}
D → ε {ε} {#}
  1. 因为S、B、C、D的SELECT集有交集且为空,所以此文法为LL(1)文法。
  2. 测试用例如下(文法推导所得,推导过程略):
    ab abb abaab ababbbbbbbbb bbbbbbbbbbbbbbbbbbbbbbbbbbb baaaaabbbb(错误用例) ab#(错误用例) abcdefg(错误用例) ABCDEFG(错误用例) 
四、实验内容及步骤

1. 用递归下降分析程序测试自己写的文法

#include<stdio.h> // 函数声明 void S(void); void B(void); void C(void); void D(void); // 定义一个长度为100的字符数组 char s[100]; // 用来作数组索引,当每次匹配成功存入数据时index自增1 int i; // 用来标记语句是否正确 int SIGN; int main() { 
    printf("please input a yuju ends with #\n"); // 一个死循环 while( 1 ) { 
    SIGN = 0;//语句是否正确用SIGN i=0; // 类似Java中的Scanner,读取输入的字符串 scanf("%s",&s[0]); // 当输入的第一个字符为#时,程序直接结束 if( s[0] == '#') return 0; S(); // 如果最后的字符以#结束则输出下面 if(s[i] == '#' && SIGN == 0){ 
    printf("This is a right yuju!\n"); }else{ 
    printf("This a wrong yuju\n"); } printf("please input a yuju ends with #\n"); } return 1; } void S() { 
    if(SIGN==0) { 
    // 当输入的字符串中首字母为a时 if(s[i]=='a'){ 
    ++i; // 自增操作 B(); }else if(s[i]=='b'){ 
    ++i; D(); }else{ 
    SIGN=1; } } } void B() { 
    if(SIGN==0){ 
    if(s[i]=='b'){ 
    ++i; C(); }else if(s[i] == '#'){ 
    SIGN=1; } } } void C() { 
    if(SIGN==0){ 
    if(s[i]=='a'){ 
    ++i; S(); }else if(s[i]=='b'){ 
    ++i; D(); }else if(s[i]!='#'){ 
    SIGN=1; } } } void D() { 
    if(SIGN==0){ 
    if(s[i]=='a'){ 
    ++i; B(); }else if(s[i]=='b'){ 
    ++i; D(); }else if(s[i]!='#'){ 
    SIGN=1; } } } 

注: 此代码正好100行,不过可以看出代码质量很差(冗余代码很多),每个函数中的功能都是一样的,应该抽取一下,代码应该可以简洁很多。

2. 测试用例测试如下
在这里插入图片描述

五、实验小结

1. 遇到的主要问题
答:
刚开始测试测试用例时,根据文法推导的句子在程序中一直报错,首先我确定自己推导没有问题,又看了程序代码好像也没有问题,找了好久没有找到,最后使用Xcode(Mac平台下由apple公司维护用来开发iPhone程序和Mac程序的一款集成开发环境)打断点通过单步调试把问题找了出来,因为我把s[i] = ‘p’ 写成了s[i] = ‘P’ 将小写字母写成了大写。这就表现出调试程序的重要性,通过调试可以看计算机如何一步步来执行程序的,对程序有更好的理解。(附上一张调试图)
在这里插入图片描述
这是S函数,当我从控制台录入pba时,第一个字符p和s[i]相同,但是当程序执行直接从39行调到了45行,没有执行if(s[i] == ‘P’)语句,我才找到上面所说的错误!



3. 得到的经验
答:
①:C语言函数声明,这和Java以及其他编程语言不相同,当在main()函数中调用其他函数时,编译器会在main()函数上面找这些函数,如果函数没有声明就会编译报错(找不到),若将函数写在main()函数上,就不会报错。
②:首先更加清晰的理解了语法分析的主要任务,它是在词法分析的基础上将单词组合起来,组成一些语句,比如说在Java中,public static void main(String[]args);方法中,如果void写在public前面编译器就会报错,那是因为编译器已经做好了语法分析的工作,说白了对源代码在结构是否正确这就是语法分析的任务。
③:理解了递归下降分析法,它是一种自顶向下的分析,根据文法来构造C函数,遇到终结符时通过和自己在屏幕中录入的数据作比较,若相同修改数组索引,这个终结符后面若是一个非终结符则调用这个非终结符的函数。一层一层的向下分析,有时会在函数体中调用自己,这就形成了递归。



版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/232674.html原文链接:https://javaforall.net

(0)
全栈程序员-站长的头像全栈程序员-站长


相关推荐

  • idea web项目部署到tomcat_系统部署步骤

    idea web项目部署到tomcat_系统部署步骤使用IDEA编辑器开发项目十分便捷,这里介绍使用IDEA编辑器添加Tomcat详细的记叙了intelliJIdea中Tomcat的部署,主要是在Tomcat部署的时候一些细节性的东西。1、新建web工程这里有一个已经创建好的web项目2、配置tomcat配置tomcat前,先确保本地已经下载并安装完成了tomcat如果不清楚如何安装tomc…

    2022年10月10日
    6
  • iptables

    iptables

    2022年3月5日
    46
  • win10闲置服务如何关闭_任务管理器中服务主机进程有什么用

    win10闲置服务如何关闭_任务管理器中服务主机进程有什么用在使用Windows10系统电脑过程中,一位用户打开任务管理器时发现一些空闲进程会占用比较多的CPU,因此想知道能否将它关闭掉。为此,小编整理了关闭方法,有需要的用户,请来看看win10系统空闲进程占用cpu怎么关闭吧。windows10系统使用过程中,会默认运行很多进程,但有许多是空闲进程,且会占用很多空间,因此win10系统空闲进程占用cpu多最好的解决方法就是关闭空闲进程,如何关闭空闲进程呢…

    2022年10月20日
    3
  • Centos搭建Ansible

    Centos搭建Ansible

    2021年6月1日
    79
  • SaaS管理软件_软件saas

    SaaS管理软件_软件saas山寨SaaS今天又有一个人问我SaaS了,而且显然看了不少资料,也总结与思索了许多。但他与我交流后,我觉得有些话我也要总结总结,我对SaaS的一些观点和想法也清晰了不少,所以记了下来。大家都把SaaS定位在中小企业的身上。这个观点我也认同。因为我遇到的客户恰恰层次比较清晰:1进货卖货当渠道的经销商。本身自己不生产不设计,只是他从厂家进货,然后自己卖了,中间打个价差而已。他们主要的业务就…

    2022年9月23日
    3
  • opkg软件包管理「建议收藏」

    opkg软件包管理「建议收藏」opkg工具(一个ipkg变种)是一个用来从本地软件仓库或互联网软件仓库上下载并安装OpenWrt软件包的轻量型软件包管理器。GNU/Linux用户可能会对apt-get,aptitude,pacman,yum等比较熟悉,也会看出其相似之处。它与NSLU2上同样用于嵌入式设备的Optware也有相似之处。OPKG没有仅仅将软件安装到一个单独的路径(如:/opt),而…

    2022年6月12日
    157

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号