【编译原理复习笔记】语法分析(一)

分类

语法分析可以按照分析方向分为两类
自顶向下/自底向上

自顶向下的分析

从分析树的顶部向底部方向构造分析树
每一步推导需要做两个选择:
(1)需要替换哪个非终结符
(2)用哪个产生式

最左推导

在最左推导中,总是选择每个句型的最左非终结符进行替换
经过最左推导得到的句型叫做最左句型

最右推导

在自底向上的分析中,总是采用最左规约的方式,因此把最左规约称为规范规约,相对应最右推导成为规范推导

递归下降分析

由于语法分析器一般从左至右读取代码,故采用最左推导
根据输入流中的下一个终结符,选择最左非终结符的有关候选式
循环过程,每个过程对应目标句子中的非终结符
问题:可能需要回溯,导致效率低

预测分析

预测分析是递归下降分析技术的特例,通过在输入中向前看固定个数 k 个符号来选择正确的 A-产生式,称为 LL(k)文法

文法转换

含有 A → A α A \to A\alpha AAα的产生式的文法称为直接左递归
如果一个文法中存在非终结符 A → + A α A \to^+ A \alpha A+Aα,那么这个文法就是左递归的
经过两步及以上产生的左递归被称为是间接左递归
左递归文法会使递归下降分析器无限循环

消除直接左递归

A → A α ∣ β , β 不以 A 开头 A\to A\alpha | \beta \\ ,\beta 不以 A 开头 AAαββ不以A开头
可以推导出 r = β α ∗ r = \beta\alpha^* r=βα
故可以写成
KaTeX parse error: Undefined control sequence: \betaA at position 6: A\to \̲b̲e̲t̲a̲A̲’
A ’ → α A ’ ∣ ϵ A’ \to \alpha A’|\epsilon AαA’∣ϵ
就避开了直接左递归,转换成了右递归

消除间接左递归

e.g.
S → A a ∣ b S \to A a|b SAab
A → A c ∣ S d ∣ ϵ A \to Ac|Sd|\epsilon AAcSdϵ
在实际推导时会出现:
S = > A a S => Aa S=>Aa
= > S d a => Sda =>Sda
出现了左递归
解决方法:将 S 产生式放入 A 产生式中,然后消除 A产生式的直接左递归

消除公共前缀

在这里插入图片描述

LL1 文法

S_文法:每个产生式的右部都以终结符开始,同一非终结符的各个候选式的首终结符都不同

产生式的后继符号集
在某个句型中紧跟在 A 后面的终结符的集合,记为 FOLLOW 集
产生式的可选集

一个产生式的可选集指的是当选用该产生式进行推导的时候,对应输入符号的集合,
e.g. S E L E C T ( A → a β ) = a SELECT(A \to a\beta) = \\{a\\} SELECT(Aaβ)=a
q_文法:每个产生式的右部为 epsilon/首字母为终结符,且具有相同左部的产生式具有不相交的可选集

串首终结符集

串首第一个符号是非终结符,简称首终结符
给定一个文法符号串 alpha,alpha 的串首终结符集 FIRST(alpha)被定义为 alpha 推导出的所有串首终结符构成的集合
对于可选集 SELECT,
如果空字符不属于 FIRST 集, S E L E C T ( A → α ) = F I R S T ( α ) SELECT(A \to \alpha) = FIRST(\alpha) SELECT(Aα)=FIRST(α)
如果空字符属于 FIRST 集, S E L E C T ( A → α ) = ( F I R S T ( a ) − ϵ ) ∪ F O L L O W ( A ) SELECT(A \to \alpha) = (FIRST(a) - \\{\epsilon\\}) \cup FOLLOW(A) SELECT(Aα)=(FIRST(a)ϵ)FOLLOW(A)

LL1 文法的定义

根据上面的概念,在文法 G 中,任意两个具有相同左部的产生式 A → α ∣ β A \to\alpha|\beta Aαβ
(1)如果 alpha 和 beta 均不能推出空字符,则 F I R S T ( α ) ∩ F I R S T ( β ) = ∅ FIRST(\alpha)\cap FIRST(\beta) = \varnothing FIRST(α)FIRST(β)=
(2)alpha 和 beta 至多有一个能够推导出空字符
如果 β = > ϵ \beta => \epsilon β=>ϵ,则 F I R S T ( α ) ∩ F O L L O W ( A ) = ∅ FIRST(\alpha)\cap FOLLOW(A) = \varnothing FIRST(α)FOLLOW(A)=
对于 alpha 同理
(3)不可能同时推出空字符,否则会产生二义性
S → α → ϵ , S → β → ϵ S \to \alpha \to \epsilon,S \to \beta \to \epsilon Sαϵ,Sβϵ

FIRST 集细究

对于一串产生式,寻找 FIRST 集方法如下:
E → T E ’ E \to TE’ ETE
E ’ → + T E ∣ ϵ E’ \to +TE|\epsilon E+TEϵ
T → F T ’ T \to FT’ TFT
T ’ → ∗ F T ’ ∣ ϵ T’ \to *FT’|\epsilon TFT’∣ϵ
F → ( E ) ∣ i d F \to (E)|id F(E)id
(1)查看各产生式右部第一个符号是否为终结符,如果为终结符,则直接填在对应左部的 FIRST 集中
在这里插入图片描述

(2)寻找空串,并将空串添加到对应的 FIRST 集中
在这里插入图片描述

(3)对于串首是非终结符的产生式,则看该非终结符下所具有的 FIRST 集合
在这里插入图片描述

不断运用这三个规则,就可以得到 FIRST 集的集合

FOLLOW 集细究

(1)首先查看开始符号的位置,开始符号算作该产生式集合所构成句型的最右符号,FOLLOW 集包含$
在这里插入图片描述

(2)观察每个式子的右部,两个连接的非终结符,后者 FIRST 集中的终结符则在前者的 FOLLOW 集中
在这里插入图片描述

(3)对于每个产生式右部的最末尾,如果其右边没有终结符,则左部的 FOLLOW 集被添加到该非终结符的 FOLLOW 集中
在这里插入图片描述

(4)对于 FIRST包含空字符的非终结符(且在右部末尾),其前面的非终结符填入左部非终结符的 FOLLOW 集
在这里插入图片描述

(5)对于右部中,一个非终结符后紧跟着一个终结符,将该终结符添加到前者的 FOLLOW 集中
在这里插入图片描述

重复以上几步作为一个循环,直到这些 FOLLOW 集不再发生变化,此时结束循环,认为找到了所有 FOLLOW 集
该例子最终的 FOLLOW 集如下所示
在这里插入图片描述

SELECT 集的细究

对于原产生式,可改写为
E → T E ’ E \to TE’ ETE
E ’ → + T E E’ \to +TE E+TE
E ’ → ϵ E’ \to \epsilon Eϵ
T → F T ’ T \to FT’ TFT
T ’ → ∗ F T ’ T’ \to *FT’ TFT
T ’ → ϵ T’ \to \epsilon Tϵ
F → ( E ) F \to (E) F(E)
F → i d F \to id Fid
在拥有了 FIRST 集和 FOLLOW 集后,判断 SELECT 集只需要以下三种分类方法:
(1)如果产生式右部第一个为终结符,则该产生式 SELECT集就为该终结符
(2)如果产生式右部第一个为非终结符,则 SELECT 集为该非终结符的 FIRST 集
(3)如果产生式右部为空字符,则 SELECT 集为产生式左部非终结符的 FOLLOW 集
遵循这三个原则,我们可以得到:
在这里插入图片描述

此时对于相同左部的产生式,其满足之前定义的 LL1 文法的要求,或者在此处直接观察 SELECT 集,red:SELECT 集不相交则说明其为 LL1 文法
所以上述文法是 LL1 文法
同时拥有了SELECT 集之后也可以很轻松的定义预测分析表:

预测分析表

在这里插入图片描述

递归的预测分析法

在递归下降分析中,编写每一个非终结符对应的过程时,根据预测分析表进行产生式的选择
e.g.
在这里插入图片描述

非递归的预测分析法

非递归的预测分析不需要为每个非终结符编写递归下降程序,而是根据预测分析表构造一个自动机,也叫表驱动的预测分析
类似有穷自动机,但是增加了栈,用于记忆,一方面从预测分析表中使用新产生式替换,另一方面当遇到目标输入时将当前终结符出栈,同时开始考虑下一个终结符
在这里插入图片描述

递归与非递归之对比

递归的预测分析表规模比较大,不需要载入预测表,而且比较直观,但是在自动生成和效率上不占优势;非递归的预测方法尽管不算特别直观且需要载入预测分析表,但是对于机器自动生成的难度来说较小,而且效率也比较高

预测分析中的错误处理

两种情况可以检测到错误

(1)栈顶的终结符和当前输入符号不匹配
(2)栈顶的非终结符与当前输入符号在预测分析表中在对应项为空

恐慌模式

忽略输入中的一些符号,直到输入中出现同步词法单元集合中的某个词法单元
一般将非终结符的 FOLLOW 集认为是同步词法单元
在这里插入图片描述

M(A,a),其中 A 表示当前栈顶符号,a 表示输入符号,如果 M = null,则表示检测到错误,根据恐慌模式忽略 a
如果遇到 synch,则弹出栈顶的非终结符 A,尝试继续分析后面的语法符号
如果栈顶此时为终结符且与输入符号不匹配,则弹出栈顶的终结符

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/pingmian/13437.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【重学C++】02 脱离指针陷阱:深入浅出 C++ 智能指针

前言 大家好,今天是【重学C】系列的第二讲,我们来聊聊C的智能指针。 为什么需要智能指针 在上一讲《01 C如何进行内存资源管理》中,提到了对于堆上的内存资源,需要我们手动分配和释放。管理这些资源是个技术活,一不…

正点原子LWIP学习笔记(一)lwIP入门

lwIP入门 一、lwIP简介(了解)二、lwIP结构框图(了解)三、如何学习lwIP(熟悉) 一、lwIP简介(了解) lwIP是一个小型开源的TCP/IP协议栈 阉割的TCP/IP协议 TCP/IP协议栈结构&#xff0…

C语言游戏实战(12):植物大战僵尸(坤版)

植物大战僵尸 前言: 本游戏使用C语言和easyx图形库编写,通过这个项目我们可以深度的掌握C语言的各种语言特性和高级开发技巧,以及锻炼我们独立的项目开发能力, 在开始编写代码之前,我们需要先了解一下游戏的基本规则…

基础2 JAVA图形编程桌面:探索图形程序的抽象实现

嘿,大家好!我非常高兴又一次有机会与大家相聚,分享新的知识和经验。对于热爱编程和探索新技术的朋友们来说,今天的内容绝对不容错过。我为大家准备了一个详尽的视频教程:《基础2 JAVA 图形编程:主程序调用…

【Python爬虫】Selenium使用

安装配置教程自行搜索 所用驱动chromedriver应与chrome浏览器版本相对应 pip install selenium 笔者selenium所用版本为4.11.2,新旧版之间会有差别 from selenium import webdriver driver webdriver.Chrome()实例化driver对象后,driver对象有一些常…

vue(十二) 组件二 动态组件(Component)和异步组件(defineAsyncComponent)

文章目录 组件注册1.全局注册2.局部注册3.组件名格式 动态组件异步组件1.基本使用2.加载与错误状态3.搭配Suspense 组件使用 组件注册 一个 Vue 组件在使用前需要先被“注册”,这样 Vue 才能在渲染模板时找到其对应的实现。组件注册有两种方式:全局注册…

git拉取项目前需要操作哪些?

1.输入 $ ssh-keygen -t rsa -C "秘钥说明" 按enter键 2.出现 ssh/id_rsa:(输入也可以不输入也可以) 然后按enter键 3.出现empty for no passphrase:(输入也可以不输入也可以) 然后按enter键 4.出现same passphrase again: (输入也可以不输入也…

程序员如何减肥

目录 基本的生化知识减肥三板斧关于减肥药 基本的生化知识 人体供能顺序。是糖原——脂肪——蛋白质,只有先将肝糖原耗尽,机体才会动用脂肪。因为糖原分解靠的是三羧酸循环,脂肪分解靠的是脂肪动员和丙酮分解。如果一个人动用蛋白质来供能&a…

linux下直接使用别人的anaconda环境,copy别人环境

1.直接使用别人的anaconda安装环境 source /home/XXX/anaconda3/bin/activate conda activate labelme 2.copy anaconda环境 cp -r /home/XXX/anaconda3/envs/x-anylabeling /home/YYY/anaconda3/envs conda config --append envs_dirs /home/YYY/anaconda3/envs conda activa…

20240516-Flyme AIOS 特种兵发布会

目录 1 Flyme AIOS 2 路演功能 2.1 拖拽流转 2.2 任务剧本自定义 2.3 智能体商店 2.4 实况通知 2.5 AI壁纸 3 MYVU 3.1 翻译功能 3.2 AR导航-骑行 3.3 AI语音转文字-科技向善 3.4 Flyme AR-提词器增强 1 Flyme AIOS 1)目标:All in AI&#…

AI绘图Stable Diffusion,如何无损高清放大图片,保姆级教程建议收藏!

前言 我们在用 stable diffusion 制作AI图片时,默认生成图片的尺寸为512*512,即使是竖图一般也就是512*768,如果再把尺寸设置大一些,就会因为硬件算力不够而造成系统崩溃,今天就来跟大家聊一聊,如何将制作…

RocketMQ-Dashboard 控制台使用详解

1 安装部署 具体部署启动请参考:RocketMQ从安装、压测到运维一站式文档_rocketmq benchmark压测-CSDN博客 RocketMq的dashboard,有运维页面,驾驶舱,集群页面,主题页面,消费者页面,生产者页面&…

[解决]静态方法不能使用泛型

public static Result<T> success(T data){Result<T> result new Result<>(data);result.setCode("200");result.setMsg("success");return result;}会报错&#xff0c;因为静态方法不能使用泛型 解决方法&#xff1a; 在static后加上…

【Kubenetes】边缘计算KubeEdge架构设计详解

文章目录 前言KubeEdge云边通信方式云端架构设计EdgeController:云到边&#xff1a;边到云 DeviceController:云到边边到云 边缘端架构设计EdgedPod的管理部分Pod的监控部分Pod的卷管理Pod的垃圾回收Pod同步管理 MetaMangger从云到边缘的更新 (Update From Cloud To Edge)从边缘…

入门篇:Kafka基础知识·

目录 一、Kafka简介 二、Kafka核心组件 三、Kafka安装与配置 1.下载与解压 2.配置环境变量 3.配置server.properties 4.启动Kafka服务 四、Kafka基本操作 1.创建Topic 2.查看Topic列表 3.发送消息 4.接收消息 五、Kafka进阶使用 1.消息持久化与存储 2.消息顺序与…

react 使用WebAssembly实战

在React中使用WebAssembly&#xff08;WASM&#xff09;的示例可以通过以下步骤实现&#xff1a; 1. 准备WebAssembly模块 首先&#xff0c;确保你有一个已编译的WebAssembly模块&#xff08;.wasm文件&#xff09;。如果你还没有&#xff0c;可以通过Emscripten等工具将C/C代…

Covalent长期数据设施,支持基于 “blob” 、总锁仓54亿美元的L2

Covalent Network&#xff08;CQT&#xff09;是领先的历史数据可用性网络&#xff0c;通过其在 Web3 中超过 225 个区块链上的结构化数据基础设施&#xff0c;为数千名客户和开发人员提供支持。Covalent Network&#xff08;CQT&#xff09;正在与未来以太坊的进步需求相匹配&…

SQL慢查询学习篇

https://www.cnblogs.com/isyues/p/17733015.html 1. 对扫到的SQL慢查询语句执行 explain explain select task_id, channel, count(task_id) as count from tablename where send_time > "2024-05-10 16:13:59" and send_time < "2024-05-14 16:13:59…

api接口、api文档、api调试、api测试

应用程序接口是一组定义、程序及协议的集合&#xff0c;通过 API 接口实现计算机软件之间的相互通信。API 的一个主要功能是提供通用功能集。程序员通过调用 API 函数对应用程序进行开发&#xff0c;可以减轻编程任务。 API 同时也是一种中间件&#xff0c;为各种不同平台提供数…

展馆展厅设计施工流程

1、需求分析和确定&#xff1a; 与客户沟通&#xff0c;了解客户需求&#xff0c;对展馆展厅的用途、面积、功能、展品特点等进行分析&#xff0c;并确定设计方案。 2、方案设计 根据需求确定设计方案&#xff0c;包括平面布局、展品陈列、展示方式、照明等。设计师需要提供设计…