编译原理笔记(哈工大编译原理)

news2025/1/6 19:15:28

文章目录

  • 前言
  • 概论
  • 语言与文法
    • 基本概念
      • 字母表
      • 字母表与串的联系
    • 文法
    • 语言
      • 推导和规约
      • 句型与句子
      • 语言与字母表
    • 文法的分类

前言

说实话,我不是很想上这门课,确实没什么大用,虽然我觉得这门课学一学也挺好,但是我觉得弄8个大实验就真的不太够意思,不如纯理论。

吐槽归吐槽,还有两天就要考试了,从现在开始我要把哈工大的课程刷完,写篇笔记,稍微刷点题,然后及格飘过。

虽然很多人说这个老师是念ppt,但是其实不然,ppt很复杂,你自己看还是有点麻烦,不如让老师给你指出顺序,这样也舒服,建议2倍速。

这课讲的确实不错,条理清晰,ppt也好看,果然群众的眼睛是雪亮的,听学校的课真不如课下听听这个。

概论

编译就是一个翻译的过程,将高级语言(源语言)翻译成汇编语言或者机器语言(目标语言)。

编译系统是一个很大的项目,从源程序到目标及其代码全部包揽,其中分为4部分,以C语言为例解释其作用:

  1. 预处理器:.c变.i。处理所有的#号语句。比如#include语句(导入模块),处理宏定义#define
  2. 编译器:.i变.s,编译系统的核心,编译原理课程研究的对象
  3. 汇编器:.s变.o,此时机器代码段已经生成,其中的机器代码都是可重定位的(只有逻辑地址)
  4. 链接器/加载器:链接器将.o代码段组合,加载器将完整的程序加载到内存中运行(转逻辑地址到物理地址)

在这里插入图片描述
我们来具体研究一下编译器的编译过程,整体上分为两个阶段,先从源语言理解出语义,变成中间代码,然后再将中间代码转化为目标的语言。这两个阶段分别叫做编译器的前端和后端。

在这里插入图片描述

整体过程其实和人类的翻译过程是很像的:

词法分析 — 单词词性,孤立个体
语法分析 — 单词组合,构造短语
语义分析 — 连词成句(纠错),直译句义
中间代码 — 抽象提取,句义意会
代码优化 — 同义替换,翻译润色
目标程序 — 翻译结果,成品输出

下面来逐一介绍:

词法分析(Scanning)就是把一整个句子,切成一个又一个单词,确定单词的类型并且打上标记,变成token

在这里插入图片描述
一词一码的单词,只需要种别码就可以了,属性值可以不要,因为已经可以区分了。对于多词一码的,需要用种别码界定大类,然后用属性值确定内容。

在这里插入图片描述

语法分析(Parsing)将词法分析的结果加工,把词串成短语,以语法树的形式输出。

在这里插入图片描述

语义分析(Semantic)比较抽象。

什么是语义呢?TODO,我感觉程序说白了就是在玩各种变量,函数,那么语义就代表着我要把变量的各种信息以及函数的各种信息都提取出来,只要把这些东西搞出来,后面转化成机器语言就很方便了。

所以语义分析的一大任务是收集标识符的属性信息,标识符无非就是变量函数这些东西,收集他们的属性就是在搞清楚他们想干点什么。

最后这些东西记录在符号表里,之所以NAME字段是<符号表中地址,长度>的格式,是为了节省空间,毕竟长度不确定,统一长度难免浪费。

在这里插入图片描述

除此之外,语义分析还要做最后一步的正确性检查,确保在进行代码生成前没有错误。

在这里插入图片描述

中间代码生成(IC-gen)。语法树其实已经是一种中间形式了,但是这种结构还是更适合人看,机器更喜欢一条一条的代码,所以ic-gen阶段将语法树转变为一条一条的中间代码,后面生成目标代码可以直接对照生成。

在这里插入图片描述

中间形式叫三地址吗,代表一条指令最多有三个操作数,一般用四元组表示,多出来的这个1指的是操作符,很像汇编语言。

给一张表,下面的地址码使用标志符表示的,不是说地址吗?这是因为,符号表里面已经记录了标志符到地址的映射,所以用标志符=用地址。

在这里插入图片描述

总结一下四元组表示的规律:

  1. 有赋值操作的
    • 一般是两个源操作数作为2,3分量,不够就空开,目标数作为第4分量
    • x[i]这种比较特殊的目标,以i作为目标数
  2. 无赋值操作的
    • 一般都只有一个目标数
    • call比较特殊,只有两个源操作数

目标代码生成(nc-gen)是吧中间形式映射到目标语言。一般是将中间代码映射到目标代码,有的人也会把语法树映射成目标代码,但是及其受限,还是要一步一步走才好。nc-gen的关键是寄存器的合理分配。

代码优化无非就是优化空间或者速度。

语言与文法

基本概念

字母表

字母表:符号的集合,一个语言中最最基本的元素集合。注意,字母表里面不一定只是一个一个的符号,也可以是串,后面就会看到的。

字母表的运算如下:

  1. 乘积。本质上就是集合乘积,即笛卡尔积
    在这里插入图片描述

  2. n次幂。幂的定义就是连续乘积。直观理解,就是长度n的字符串集合。照这么理解,其中0次幂的结果是空串集(长度为0的字符串集合),而不是空集,也就很合理了。
    在这里插入图片描述

  3. 正闭包。这个也是离散数学上的概念,直观理解为任意长度的字符串集合,正即不包含空串
    在这里插入图片描述

  4. 克林闭包(Kleene closure)。相比于正闭包,多了一个空串。
    在这里插入图片描述

字符串是一个老生常谈的概念,其实就是字母表上字符的任意有序排列组合(包括空串),用规范的语言说,就是字母表克林闭包的元素。

字符是语言中最基本的元素,那串就是语言中最常用的基本元素,字符本身其实也算是一种串,串是一个更大的概念。

在这里插入图片描述
来看下运算:

  1. 连接。就连起来而已,由此引申出前后缀的概念,这是相对的,有前缀就有后缀,甚至于空串都可以作为前后缀。
    在这里插入图片描述
  2. 幂。n次幂=连接n次
    在这里插入图片描述

字母表与串的联系

其实到这里你就可以发现,这两个东西似乎有一种本质的联系,说白了就是集合和元素的关系。

你会发现,串的连接运算与字母表的乘积对应,串的连接结果 ∈ \in 字母表乘积。串的任意组合对应着字母表的乘积组合,任意串对应着字母表的克林闭包。

其实就是元素和集合的关系啊,有趣。

文法

什么是文法?用抽象一点的话说,就是表示了基本符号如何构成语法成分,以及语法成分如何进一步组成更宏观的语法成分。

蚌埠住了吧,直接看例子吧。对于自然语言,基本符号是单词,语法成分是短语和句子。倒数4个介绍了基本元素如何构成语法成分,而前几条介绍了语法成分如何组合成更宏观的语法成分。

想一想语法树,是不是一层一层的,我们这个构成其实也是从下到上一层一层的。

下图仅仅是针对自然语言的,基本符号是单词,语法成分是短语和句子,如果是针对单词来说,那么基本符号就是字母,语法成分就是单词。

在这里插入图片描述

为了便于计算机处理和理解,我们用数学语言(形式化语言)去描述文法。总的来说,一部文法规定了一个语言的各种成分,以及转化规则:

  1. 终结符对应基本符号
  2. 非终结符对应语法成分
  3. 产生式集合P对应这些成分之间的转化关系
  4. 开始符号S对应最大的语法成分,所以开始符号归属于非终结符也是很合理的。

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

一部文法的元素集合其实在产生式里面就可以看出来,所以不引起歧义的情况下,甚至只写P都可以。所以我们重点研究一下产生式的表示:

这是最基本的写法,左边到右边是一个箭头,从左到右是分解,从右到左是合并。

在这里插入图片描述

P还可以继续简化,相同左部的产生式可以合并为一个,右边用|隔开,代表或,右边的每一项都叫候选式。

在这里插入图片描述

最后说下符号约定,好复杂,我感觉不用记那么多,后面慢慢就都记住了,所以这里只把基本规律放出来:

在这里插入图片描述

语言

推导和规约

什么是语言?此处直接给出定义:句子的集合

听起来有点像字母表,其实字母表也算是一种很简单的语言,而我们的语言集合,可以是无穷的集合,因为语言集合是从文法推导出来的,可以说,文法与语言是对应关系。

如何判断一个句子是否属于一个语言呢?还是要着眼于文法。一条文法,从左到右是分解,我们这里叫做推导,从右到左是合并,我们叫规约

推导分为0步(没推导),1步(直接推导),n步(n步推导)
在这里插入图片描述

直接看例子吧。

在这里插入图片描述
在这里插入图片描述

句型与句子

我们说,终结符构成的串就是语言的一个句子,那我们在推导过程中产生的中间形式,里面又有终结符,又有非终结符,甚至全是非终结符,这又叫什么呢?句型

句型是比较抽象的,不具体的,所以就叫“型”,而句子就是一个完全的终结符串,句子也可以理解为特殊的句型。

在这里插入图片描述

语言与字母表

回归语言的定义,语言和字母表的元素都可以是字符串,那他们到底不同在哪里呢?本质在于,字母表是我们直接给出的集合,而语言是通过文法推导出来的。

所以我们说L(G)是文法G生成的语言L。给定一部文法,很有可能生成一个无穷集合,这就是用有限的文法表示无穷的句子,这就是语言的本质,用元素+规则表达无穷的组合。

在这里插入图片描述

我们来具体举几个例子。下面这部文法表示的是标识符,4条文法就表示出了标识符这个语言,而我们知道,标识符是无穷的:

  1. L和D可以直接指向终结符,分别代表字母和数字
  2. T总的来说,表达的意思就是L和D的任意组合,只要不是空串就行
  3. S=L或者LT,这告诉我们标识符一定要以字母(L)开头,剩下的部分字母数字随意组合就好(T)

在这里插入图片描述

最后再重申一下语言和标识符的关系,区别仅仅在于怎么生成的,他们从成分上来说,其实是一样的,或者说字母表本就是一种语言。由此,运算其实是可以套用的,甚至可以把字母表通过语言的运算转化成更复杂的语言:

在这里插入图片描述

由此,串的运算,集合的运算,文法的推导,这三个东西其实是统一的。

文法的分类

0123四类文法。

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

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

相关文章

socket地址的通配符地址、环回地址

今天在写ServerSocket的时候&#xff0c;遇到了socket地址的通配符地址、环回地址。 package com.thb;import java.io.IOException; import java.net.InetAddress; import java.net.ServerSocket;public class ServerSocketMain {public static void main(String[] args) {try…

UI Tool Kit 使用

Unity 2021 已经把UIBuilder 内置了&#xff0c;项目组也打算 后续工具采用 toolkit来写&#xff0c;这边也是找了一下教程熟悉了一下。 UI 工具包 - Unity 手册 首先 先创建一个EditorWindow 会生成相应的C#&#xff0c;UXML,USS代码 默认会把显示的MenuItem代码生成&#xf…

记录--设计一个可选择不连续的时间范围的日期选择器

这里给大家分享我在网上总结出来的一些知识&#xff0c;希望对大家有所帮助 npm包&#xff1a;sta-datepicker效果图 需求 普通的时间选择器要么只能单选&#xff0c;要么只能选范围&#xff0c;不可以随意选择若干个时间&#xff0c;同时大多数现成的时间选择器选择结束会收起…

EasyExcel实战与笔记

概述 Excel导入导出是业务开发中非常常见的需求。本文记录一下如何快速入门使用EasyExcel&#xff0c;深度实战&#xff0c;以及遇到的问题。 入门 使用EasyExcel导入如下依赖即可&#xff1a; <dependency><groupId>com.alibaba</groupId><artifactI…

java-代码生成器——有了代码生成器两个小时的工作量2分钟完成了

代码生成器 &#x1f942;代码生成器&#x1f33b;1. 第一步引用相关依赖&#x1f357;2. 第二步编写代码 CodeGet.java&#x1f969;3. 第三步运行查看结果&#x1f356;4. 第四步总结一下 &#x1f942;代码生成器 只需要创建好表的结构&#xff0c;代码生成器通过简单的配置…

Linux知识点 -- 进程控制(二)

Linux知识点 – 进程控制&#xff08;二&#xff09; 文章目录 Linux知识点 -- 进程控制&#xff08;二&#xff09;一、进程程序替换1.概念2.替换原理3.进程替换的操作4.使用exec函数执行自己写的程序5.使用exec函数执行其他语言的程序 二、编写一个简易的shell 一、进程程序替…

LeetCode 892. Surface Area of 3D Shapes【数组,数学】简单

本文属于「征服LeetCode」系列文章之一&#xff0c;这一系列正式开始于2021/08/12。由于LeetCode上部分题目有锁&#xff0c;本系列将至少持续到刷完所有无锁题之日为止&#xff1b;由于LeetCode还在不断地创建新题&#xff0c;本系列的终止日期可能是永远。在这一系列刷题文章…

KCC@北京启动,为一个城市做好开源!

KCC&#xff08;开源社城市社区&#xff09;北京区在6月12日正式成立&#xff0c;吸引了众多开源爱好者和技术开发者参与。现场举行的活动围绕 “为一个城市做好开源” 的话题展开讨论&#xff0c;包括开发者关系、开源背后的无用之用、开源在中国的变化、开源的困难与挑战以及…

OpenAI ChatGPT 使用示例

1.编程应用 1.1. 生成例子代码 ChatGPT帮助我们生产我们需要的例子代码。而且准确率很高。即使你不懂某一种语言也没关系&#xff0c;一定程度上较低了程序员的的门槛。 我有三组数据&#xff0c;第一组是星期一到星期五&#xff0c;第二组是这一天的具体时间&#xff0c;第三…

etcd 备份操作---马哥教育

etcd安装&#xff1a; mkdir -pv etcd-download-test tar -zxvf etcd-v3.4.4-linux-amd64.tar.gz -C etcd-download-test/ 编辑修改系统环境变量 /etc/profile export ETCD_HOME/tmp/etcd-download-test/etcd-v3.4.4-linux-amd64 export PATH$PATH:$JAVA_HOME/bin:$ETCD_HOM…

html实现好看的个人介绍,个人主页模板2(附源码)

文章目录 1.设计来源1.1 主界面1.2 关于我界面1.3 项目演示界面1.4 联系我界面 2.效果和源码2.1 动态效果2.2 源代码2.3 源码目录 源码下载 作者&#xff1a;xcLeigh 文章地址&#xff1a;https://blog.csdn.net/weixin_43151418/article/details/131257976 html实现好看的个人…

老胡的周刊(第095期)

老胡的信息周刊[1]&#xff0c;记录这周我看到的有价值的信息&#xff0c;主要针对计算机领域&#xff0c;内容主题极大程度被我个人喜好主导。这个项目核心目的在于记录让自己有印象的信息做一个留存以及共享。 &#x1f3af; 项目 tabby[2] 自托管的 AI 编码助手&#xff0c;…

230617安装SqlServer2017Express后,再安装一个SqlServer2017ExpressAdvanced

230616安装SqlServer2017Express 下载地址 选择语言 Microsoft SQL Server 2017 Express 下载地址: 简体中文 感谢下载 Microsoft SQL Server 2017 Express 获得下载软件 我将下载的文件的名称加上了SHA256值, 一长串 是一个 .exe 的自解压文件, 双击后,默认解压到同根文件夹…

计组期末模拟(补充)

单选题 2-1&#xff08;本题考查课程目标2&#xff09; 某计算机有 16 个通用寄存器&#xff0c;采用 32 位定长指令字&#xff0c;操作码字段&#xff08;含寻址方式位&#xff09;为 8 位&#xff0c;Store 指令的源操作数和目的操作数分别采用寄存器直接寻址和基址寻址方式…

PHP intval()函数详解,intval()函数漏洞原理及绕过思路

「作者主页」&#xff1a;士别三日wyx 「作者简介」&#xff1a;CSDN top100、阿里云博客专家、华为云享专家、网络安全领域优质创作者 「推荐专栏」&#xff1a;对网络安全感兴趣的小伙伴可以关注专栏《网络安全入门到精通》 intval 一、进制自动转换二、转换数组三、转换小数…

#systemverilog# 之 event region 和 timeslot 仿真调度(三)Verdi 辅助查看

前面的几篇文章,我们对SV仿真调度进行了理论分析和实战演练。那么工具厂商,对该类问题有没有提供相应的支持。这个应该是肯定的。因为我们知道,SV只是出于定义标准的角度,规定了仿真调度事件原理。但是具体实施细节,应是每家EDA仿真工具厂商根据自家的软件开发算法而定的。…

MySQL - 第3节 - MySQL数据类型

1.数据类型的作用 数据类型的作用&#xff1a; • 决定了存储数据时应该开辟的空间大小。 • 决定了如何识别一个特定的二进制序列。 • 决定了数据的取值范围。 2.数据类型分类 注&#xff1a;MySQL本身是不支持bool类型的&#xff0c;当把一个数据设置成bool类型时&#xff0…

NetMock 简介:简化 Java、Android 和 Kotlin 多平台中的 HTTP 请求测试

NetMock 简介&#xff1a;简化 Java、Android 和 Kotlin 多平台中的 HTTP 请求测试 NetMock可让我们摆脱在测试环境中模拟请求和响应的复杂性。 NetMock是一个功能强大、用户友好的库&#xff0c;旨在简化模拟HTTP请求和响应的过程。 对开发者来说&#xff0c;测试HTTP请求经…

稳定?国企也裁员!

大家好&#xff0c;我是爱搞事情的了不起&#xff01; 我所在的公司是一家央企下面的子公司&#xff0c;号称“国企”。 提起国企&#xff0c;好多人的印象中是855不加班&#xff0c;不裁员&#xff0c;真实情况是这样吗&#xff1f; 当国企领导 去年过年聚会&#xff0c;一个部…