通过一个专门管翻译的机器——编译器。
一、编译器是什么
源程序→预处理器→经过预处理的源程序→编译器→汇编语言程序→汇编器→可重定位的机器代码→链接器/加载器→目标机器代码。
编译器的结构:
与源语言相关:字符流→词法分析器→词法单元流→语法分析器→语法树→语义分析器→语法树→中间代码生成器→
中间表示形式→机器无关代码优化器→中间表示形式→
与目标语言相关:目标代码生成器→目标机器语言→机器相关代码优化器→目标机器语言
二、编译时,内存如何分配?
运行时存储分配——堆栈内存分配策略
静态存储分配:对于编译时刻就可以确定大小的数据对象,可以在编译时刻就为它们分配存储空间。
动态存储分配:编译时仅产生各种必要的信息,在运行时刻再动态地分配数据对象的存储空间。
堆和栈是相对于动态而言的。
所以运行时内存分为以下三大部分,动态区又有自己的三部分。
静态代码区
静态数据区
动态数据区域 栈区
空闲内存
堆区
栈和堆分别在空闲内存地址两端,他俩大小随程序运行而变化。
栈存储了活动记录,过程调用时生成并进栈,过程返回时出栈,
堆存放长生命周期的数据对象
静态存储分配的限制条件:数组上下界必须是常数;不允许过程的递归调用;不允许动态建立数据实体;
栈式存储分配:对于函数(或者叫过程、方法),几乎所有编译器都把他们的运行时刻存储以栈的形式进行管理,称为栈式存储分配。
当一个过程被调用时,该过程的活动记录被压入栈;当过程结束时,该活动记录被弹出栈。
这种安排不仅允许活跃时段不交叠的过程调用之间共享空间,而且允许以如下方式为一个过程编译代码:它的非局部变量的相对地址总是固定的,和过程调用序列无关。
(扩展概念——活动树:用来描述程序运行期间控制进入和离开各个活动的情况的数称为活动树。
树中每个结点对应于一个活动。跟结点是启动程序执行的main函数的活动。
在表示函数p的某个活动的结点上,其子结点对应于被p的这次活动调用的各个过程的活动。按照这些活动被调用的顺序,自左向右地显示它们。一个子结点必须在其右兄弟结点的活动开始之前结束。)
变长数据的存储分配:在编译时刻不能确定大小的对象,将被分配在堆区。但是,如果它们是过程的局部对象,也可以将它们分配在运行时刻栈中。
尽量将对象放置在栈区的原因:可以避免对它们的空间进行垃圾回收,也就减少了相应的开销。
只有一个数据对象局部于某个函数,且当此函数结束时它变得不可访问,才可以使用栈为这个对象分配空间。
访问链:静态作用域规则——只要函数b的声明,嵌套在函数a的声明里,那么函数b就可以访问函数a中声明的对象。
可以在相互嵌套的函数的活动记录之间,建立一种称为访问链的指针,使得内嵌的函数访问外层函数中声明的对象。
如果函数b在源码中,直接嵌套在函数a中,那么b的人和活动中的访问链都指向最近的a的活动。
三、既然这样编译,那代码就这样优化
要优化先要梳理代码,就是将代码看作流图,流图由若干块儿组成。
优化分类:
机器无关优化——针对中间代码;机器相关优化——针对目标代码;
或局部代码优化——单个基本块范围的优化;全局代码优化——面向多个基本块的优化
常用的优化方法:删除公共子表达式、常量合并、代码移动、强度削弱、删除归纳变量。
什么是代码移动:指那些不管循环多少次都得到相同结果的表达式,即循环不变计算,在进入循环前就对他们求值。
什么是强度削弱:用快的操作代替慢的操作,如用加代替乘。
什么是归纳变量:对于一个变量x,如果存在一个正或负的常数c使得每次x被赋值时,他的总值总是增加c,那么x就称为归纳变量。在沿着循环运行时,如果有一组归纳变量的值得变化保持步调一致,常常可以将这组变量删除为只剩一个
删除公共子表达式:意思就是公共部分的运算,可以用赋值的形式代替。另外,赋值操作,也尽量能省则省。
综上,代码优化的宗旨就是减少计算>赋值代替>减少赋值

认真学习系列:编译原理——B站笔记相关推荐

  1. 编译原理期末速成笔记

    哈喽大家好,又要考试了,在这里分享一下我的两天速成笔记,参考视频为哔站 Deeplei_ 的<编译原理期末速成>.本文仅是知识点总结,至于考试内容待我研究一下,后续我会再发文对考试的各个模 ...

  2. 最近想学习一下编译原理,做一个编程规范的检测工具

    因为公司对编程规范要求的很严格,然而很多人却都没有规范的习惯,所以很多问题还是存在于代码中.有一次机会想做一个编程规范检测的工具,可惜自己能力有限,很多东西都不会.偶然想到了编译原理,可惜我没学过.拿 ...

  3. 编译原理期末复习笔记

    编译原理这门课通过证明是可以速成的. 我说的"速成"是平时还要支棱一只耳朵听课哦. 其实后面几次课听了之后仿佛掌握到了其中精髓. 还有就是这门课复习起来很爽,因为复习过程可以感悟到 ...

  4. 认真学习系列:操作系统——视频+读书笔记

    此笔记分为两部分, 上部分是B站操作系统考研课程的知识点总结,包括:概述.进程与线程.处理机调度算法.进程同步.内存管理.文件管理.IO管理,共7部分. 下部分是阅读<现代操作系统>这本书 ...

  5. 编译原理 龙书 笔记

    DFA NFA CFG DFA的定义: A = ( Σ, S, s0, F, N ) Σ: 输入字母表(alphabet),是一个输入字符的集合. S:状态的集合s0: 初始状态F:终止状态集合 F ...

  6. [系列][编译原理]正则表达式

    关于正则表达式,作为软件工程师应该比较熟悉了.所谓正则表达式,就是表示字符串的格式.正则表达式r完全由它所匹配的串集来定义.这个集合称为由正则表达式生成的语言,写作L(r).此处的语言只是表示&quo ...

  7. 从0开始的python学习:编译原理实验4:语法分析器1--预测分析器构造

    这里刚开始试用python的函数功能,可能把局部变量和全局变量给写乱了,后期交之前还想再优化的时候发现越改越乱,太真实的hhh 实验四:语法分析器1–预测分析器构造 实验目的: 通过编写一个预测分析器 ...

  8. 对学习编译原理的看法

    我认为编译原理这本书是一门与代码做斗争的课程,学习编译原理能够追寻程序设计语言的本质,了解计算机各种语言编译的原理.学习了编译原理能够更加深入的了解计算机各种高级语言使用的原理,能使自己更加容易更加好 ...

  9. 编译原理第三版王生原pdf_CS143:编译原理 | 环境搭建HelloWorld

    本文使用 Zhihu On VSCode 创作并发布 本文是本人新开的坑的第一篇博客,另一个坑请看MIT 6.828 实现操作系统.从另一个坑的第一篇复制两段话: 写成博客的目的是防止自己走马观花,花 ...

最新文章

  1. SHELL基础学习必杀技之十三问
  2. 开发日记-20190905 关键词 Linux (Ubuntu) 下的Android模拟器:Genymotion
  3. Python 已经饱和?我猜你一定不懂这个技能!
  4. Linux学习之遇到的小问题---查看系统版本,虚拟机创建共享文件夹,用到的命令记录。
  5. java8 按条件过滤集合
  6. 怎么检测声音频率和幅值_【电缆小课堂】国网天津电缆公司电缆带电检测团队介绍及典型案例分析...
  7. git如何合并指定文件内容_Git合并指定文件到另一个分支
  8. 【标准】ISO14001:2015新版标准正式发布
  9. 使用golang实现对请求签名和验签
  10. PCB设计培训,Layout工程师培训,射频基带技术培训,硬件技术培训,驱动开发培训
  11. linux clac countif的使用
  12. 从零建造一个基于深度强化学习的期货日内高频交易模型(一)下载数据
  13. 2007年国内主流CMS系统及演示站点
  14. Android Poco初始化时,不大起眼但可能存在坑点的参数们
  15. 2022-2028年中国渗滤液行业市场运行态势及发展战略研究报告
  16. 年度Java技术盘点,懂这些技术的程序员2019年薪资翻倍!
  17. java 文件格式转换
  18. OpenFOAM不可压求解器pimpleFoam研究(一)粘度实现
  19. 智能识别收货地址 javascript地址智能识别
  20. 【高德地图】易采坑合集

热门文章

  1. WebBrowser提交submit后界面不刷新的解决办法
  2. 僵尸矩阵 · Zombie in Matrix
  3. 1248. 统计「优美子数组」
  4. 2020统计局的行政划分表_天津市第七次全国人口普查区域划分与地图绘制试点工作在西青区开展...
  5. 【毕设】JAVA+SQL办公自动化系统(源代码+论文+外文翻译)
  6. drain open 线与_再转一个:push-pull and open-drain,开漏(open drain)和开集(open collector...
  7. 99数据集预处理_深度学习在放射治疗的应用—工具篇(五)数据集构建
  8. C++循环语句的效率
  9. linux 查看蓝牙_华为MagicBook锐龙版双系统折腾记四:蓝牙
  10. TestComplete使用关键字测试的数据驱动测试(上)