典型的编译器可以划分成几个逻辑阶段

典型的编译器可以划分成几个逻辑阶段,第1张

这是我们今天的作业,

典型的编译器可以划分成七个主要的逻辑阶段,分别是词法分析器、语法分析器、语义分析器、中间代码生成器、独立于机器的代码优化器、代码生成器、依赖于机器的代码优化器。各阶段的主要功能:

(1)词法分析器:词法分析阅读构成源程序的字符流,按编程语言的词法规则把它们组成词法记号流。

(2)语法分析器:按编程语言的语法规则检查词法分析输出的记号流是否符合这些规则,并依据这些规则所体现出的该语言的各种语言构造的层次性,用各记号的第一元建成一种树形的中间表示,这个中间表示用抽象语法的方式描绘了该记号流的语法情况。

(3)语义分析器:使用语法树和符号表中的信息,依据语言定义来检查源程序的语义一致性,以保证程序各部分能有意义地结合在一起。它还收集类型信息,把它们保存在符号表或语法树中。

(4)中间代码生成器:为源程序产生更低级的显示中间表示,可以认为这种中间表示是一种抽象机的程序。

(5)独立于机器的代码优化器:试图改进中间代码,以便产生较好的目标代码。通常,较好是指执行较快,但也可能是其他目标,如目标代码较短或目标代码执行时能耗较低。

(6)代码生成器:取源程序的一种中间表示作为输入并把它映射到一种目标语言。如果目标语言是机器代码,则需要为源程序所用的变量选择寄存器或内存单元,然后把中间指令序列翻译为完成同样任务的机器指令序列。

(7)依赖于机器的代码优化器:试图改进目标机器代码,以便产生较好的目标机器代码。

习题一、单项选择题

1、将编译程序分成若干个“遍”是为了 。

a.提高程序的执行效率

b.使程序的结构更加清晰

c.利用有限的机器内存并提高机器的执行效率

d.利用有限的机器内存但降低了机器的执行效率

2、构造编译程序应掌握 。

a.源程序 b.目标语言

c.编译方法 d.以上三项都是

3、变量应当 。

a.持有左值 b.持有右值

c.既持有左值又持有右值 d.既不持有左值也不持有右值

4、编译程序绝大多数时间花在 上。

a.出错处理 b.词法分析

c.目标代码生成 d.管理表格

5、 不可能是目标代码。

a.汇编指令代码 b.可重定位指令代码

c.绝对指令代码 d.中间代码

6、使用 可以定义一个程序的意义。

a.语义规则 b.词法规则

c.产生规则 d.词法规则

7、词法分析器的输入是 。

a.单词符号串 b.源程序

c.语法单位 d.目标程序

8、中间代码生成时所遵循的是- 。

a.语法规则 b.词法规则

c.语义规则 d.等价变换规则

9、编译程序是对 。

a.汇编程序的翻译 b.高级语言程序的解释执行

c.机器语言的执行 d.高级语言的翻译

10、语法分析应遵循 。

a.语义规则 b.语法规则

c.构词规则 d.等价变换规则

解答

1、将编译程序分成若干个“遍”是为了使编译程序的结构更加清晰,故选b。

2、构造编译程序应掌握源程序、目标语言及编译方法等三方面的知识,故选d。

3、对编译而言,变量既持有左值又持有右值,故选c。

4、编译程序打交道最多的就是各种表格,因此选d。

5、目标代码包括汇编指令代码、可重定位指令代码和绝对指令代码3种,因此不是目标代码的只能选d。

6、词法分析遵循的是构词规则,语法分析遵循的是语法规则,中间代码生成遵循的是语义规则,并且语义规则可以定义一个程序的意义。因此选a。

7、b 8、c 9、d 10、c

二、多项选择题

1、编译程序各阶段的工作都涉及到 。

a.语法分析 b.表格管理 c.出错处理

d.语义分析 e.词法分析

2、编译程序工作时,通常有 阶段。

a.词法分析 b.语法分析 c.中间代码生成

d.语义检查 e.目标代码生成

解答

1.b、c 2 a、b、c、e

三、填空题

1、解释程序和编译程序的区别在于 。

2、编译过程通常可分为5个阶段,分别是 、语法分析 、代码优化和目标代码生成。 3、编译程序工作过程中,第一段输入是 ,最后阶段的输出为 程序。

4、编译程序是指将 程序翻译成 程序的程序。 解答

是否生成目标程序 2、词法分析 中间代码生成 3、源程序 目标代码生成 4、源程序 目标语言

一、单项选择题

1、文法G:S→xSx|y所识别的语言是 。

a xyx b (xyx) c xnyxn(n≥0) d xyx

2、文法G描述的语言L(G)是指 。

a L(G)={α|S+ ⇒α , α∈VT} b L(G)={α|S⇒α, α∈VT}

c L(G)={α|S⇒α,α∈(VT∪VN)} d L(G)={α|S+ ⇒α, α∈(VT∪VN)}

3、有限状态自动机能识别 。

a 上下文无关文法 b 上下文有关文法

c正规文法 d 短语文法

4、设G为算符优先文法,G的任意终结符对a、b有以下关系成立 。

a 若f(a)>g(b),则a>b b若f(a)<g(b),则a<b

c a~b都不一定成立 d a~b一定成立

5、如果文法G是无二义的,则它的任何句子α 。

a 最左推导和最右推导对应的语法树必定相同

b 最左推导和最右推导对应的语法树可能不同

c 最左推导和最右推导必定相同

d 可能存在两个不同的最左推导,但它们对应的语法树相同

6、由文法的开始符经0步或多步推导产生的文法符号序列是 。

a 短语 b句柄 c 句型 d 句子

7、文法G:E→E+T|T

T→TP|P

P→(E)|I

则句型P+T+i的句柄和最左素短语为 。

aP+T和i b P和P+T c i和P+T+i dP和T

8、设文法为:S→SA|A

A→a|b

则对句子aba,下面 是规范推导。

a SÞSAÞSAAÞAAAÞaAAÞabAÞaba

b SÞSAÞSAAÞAAAÞAAaÞAbaÞaba

c SÞSAÞSAAÞSAaÞSbaÞAbaÞaba

d SÞSAÞSaÞSAaÞSbaÞAbaÞaba

9、文法G:S→b|∧(T)

T→T,S|S

则FIRSTVT(T) 。

a {b,∧,(} b {b,∧,)} c{b,∧,(,,} d{b,∧,),,}

10、产生正规语言的文法为 。

a 0型 b 1型 c 2型 d 3型

11、采用自上而下分析,必须 。

a 消除左递归 b 消除右递归 c 消除回溯 d 提取公共左因子

12、在规范归约中,用 来刻画可归约串。

a 直接短语 b 句柄 c 最左素短语 d 素短语

13、有文法G:E→ET|T

T→T+i|i

句子1+28+6按该文法G归约,其值为 。

a 23 B 42 c 30 d 17

14、规范归约指 。

a 最左推导的逆过程 b 最右推导的逆过程

c 规范推导 d 最左归约的逆过程

[解答]

1、选c。

2、选a。

3、选c。

4、虽然a与b没有优先关系,但构造优先函数后,a与b就一定存在优先关系了。所以,由f(a)>g)(b)或f(a)<g(b)并不能判定原来的a与b之间是否存在优先关系:故选c。

5、如果文法G无二义性,则最左推导是先生长右边的枝叶:对于d,如果有两个不同的是了左推导,则必然有二义性。故选a。

6、选c。

7、由图2-8-1的语法树和优先关系可以看出应选b。

8、规范推导是最左推导,故选d。

9、由T→T,…和T→(… 得FIRSTVT(T))={(,,)};

由T→S得FIRSTVT(S)⊂FIRSTVT(T),而FIRSTVT(S)={b,∧,(};即

FIRSTVT(T)={b,∧,(,,}; 因此选c。

10、d 11、c 12、b 13、b 14、b

二、多项选择题

1、下面哪些说法是错误的 。

a 有向图是一个状态转换图 b 状态转换图是一个有向图

c有向图是一个DFA dDFA可以用状态转换图表示

2、对无二义性文法来说,一棵语法树往往代表了 。

a 多种推导过程 b 多种最左推导过程 c一种最左推导过程

d仅一种推导过程 e一种最左推导过程

3、如果文法G存在一个句子,满足下列条件 之一时,则称该文法是二义文法。

a 该句子的最左推导与最右推导相同

b 该句子有两个不同的最左推导

c 该句子有两棵不同的最右推导

d 该句子有两棵不同的语法树

e该句子的语法树只有一个

4、有一文法G:S→AB

A→aAb|ε

B→cBd|ε

它不产生下面 集合。

a {anbmcndm|n,m≥0} b {anbncmdm|n,m>0}

c {anbmcmdn|n,m≥0} d {anbncmdm|n,m≥0}

e {anbncndn|n≥0}

5、自下而上的语法分析中,应从 开始分析。

a 句型 b 句子 c 以单词为单位的程序

d 文法的开始符 e 句柄

6、对正规文法描述的语言,以下 有能力描述它。

a0型文法 b1型文法 c上下文无关文法 d右线性文法 e左线性文法

解答 1、e、a、c 2、a、c、e 3、b、c、d 4、a、c 5、b、c 6、a、b、c、d、e

三、填空题

1、文法中的终结符和非终结符的交集是 。词法分析器交给语法分析器的文法符号一定是 ,它一定只出现在产生式的 部。

2、最左推导是指每次都对句型中的 非终结符进行扩展。

3、在语法分析中,最常见的两种方法一定是 分析法,另一是 分析法。

4、采用 语法分析时,必须消除文法的左递归。

5、 树代表推导过程, 树代表归约过程。

6、自下而上分析法采用 、归约、错误处理、 等四种 *** 作。

7、Chomsky把文法分为 种类型,编译器构造中采用 和 文法,它们分别产生 和 语言,并分别用 和 自动机识别所产生的语言。

解答 1、空集 终结符 右

2、最左

3、自上而上 自下而上

4、自上而上

5、语法 分析

6、移进 接受

7、4 2 型 3型 上下文无关语言 正规语言 下推自动机 有限

四、判断题

1、文法 S→aS|bR|ε描述的语言是(a|bc) ( )

R→cS

2、在自下而上的语法分析中,语法树与分析树一定相同。 ( )

3、二义文法不是上下文无关文法。 ( )

4、语法分析时必须先消除文法中的左递归。 ( )

5、规范归约和规范推导是互逆的两个过程。 ( )

6、一个文法所有句型的集合形成该文法所能接受的语言。 ( )

解答 1、对 2、错 3、错 4、错 5、错 6、错

五、简答题

1、句柄 2、素短语 3、语法树 4、归约 5、推导

[解答]

1、句柄:一个句型的最左直接短语称为该句型的句柄。

2、素短语:至少含有一个终结符的素短语,并且除它自身之外不再含任何更小的素短语。

3、语法树:满足下面4个条件的树称之为文法G[S]的一棵语法树。

①每一终结均有一标记,此标记为VN∪VT中的一个符号;

②树的根结点以文法G[S]的开始符S标记;

③若一结点至少有一个直接后继,则此结点上的标记为VN中的一个符号;

④若一个以A为标记的结点有K个直接后继,且按从左至右的顺序,这些结点的标记分别为X1,X2,…,XK,则A→X1,X2,…,XK,必然是G的一个产生式。

4、归约:我们称αγβ直接归约出αAβ,仅当A→γ 是一个产生式,且α、β∈(VN∪VT)。归约过程就是从输入串开始,反复用产生式右部的符号替换成产生式左部符号,直至文法开始符。

5、推导:我们称αAβ直接推出αγβ,即αAβÞαγβ,仅当A→ γ 是一个产生式,且α、β∈(VN∪VT)。如果α1Þα2Þ…Þαn,则我们称这个序列是从α1至α2的一个推导。若存在一个从α1αn的推导,则称α1可推导出αn。推导是归约的逆过程。

六、问答题

1、给出上下文无关文法的定义。

[解答]

一个上下文无关文法G是一个四元式(VT,VN,S, P),其中:

●VT是一个非空有限集,它的每个元素称为终结符号;

●VN是一个非空有限集,它的每个元素称为非终结符号,VT∩VN=Φ;

●S是一个非终结符号,称为开始符号;

●P是一个产生式集合(有限),每个产生式的形式是P→α,其中,P∈VN,

α∈(VT∪VN)。开始符号S至少必须在某个产生式的左部出现一次。

2、文法G[S]:

S→aSPQ|abQ

QP→PQ

bP→bb

bQ→bc

cQ→cc

(1)它是Chomsky哪一型文法?

(2)它生成的语言是什么?

[解答]

(1)由于产生式左部存在终结符号,且所有产生式左部符号的长度均小于等于产生式右部的符号长度,所以文法G[S]是Chomsky1型文法,即上下文有关文法。

(2)按产生式出现的顺序规定优先级由高到低(否则无法推出句子),我们可以得到:

SÞabQÞabc

SÞaSPQÞaabQPQÞaabPQQÞaabbQQÞaabbcQÞaabbcc

SÞaSPQÞaaSPQPQÞaaabQPQPQÞaaabPQQPQÞaaabPQPQQÞaaaPPQQQÞ

aaabbPqqqÞaaabbQQQÞaaabbbcQQÞaaabbbccQÞaaabbbccc

……

于是得到文法G[S]生成的语言L={anbncn|n≥1}

3、按指定类型,给出语言的文法。

L={aibj|j>i≥1}的上下文无关文法。

解答

(1)由L={aibj|j>i≥1}知,所求该语言对应的上下文无关文法首先应有S→aSb型产生式,以保证b的个数不少于a的个数;其次,还需有S→Sb或S→bS型的产生式,用以保证b的个数多于a的个数;也即所求上下文无关文法G[S]为:

G[S]:S→aSb|Sb|b

4、有文法G:S→aAcB|Bd

A→AaB|c

B→bScA|b

(1)试求句型aAaBcbbdcc和aAcbBdcc的句柄;

(2)写出句子acabcbbdcc的最左推导过程。

解答(1)分别画出对应两句型的语法树,如图2-8-2所示

句柄:AaB Bd

图2-8-2 语法树

(2)句子acabcbbdcc的最左推导如下:

SÞaAcBÞaAaBcBÞacaBcBÞacabcBÞacabcbScAÞacabcbBdcA

ÞacabcbbdcAÞacabcbbdcc

5、对于文法G[S]:

S→(L)|aS|a L→L, S|S

(1)画出句型(S,(a))的语法树。(2)写出上述句型的所有短语、直接短语、句柄和素短语。

解答

(1)句型(S,(a))的语法树如图2-8-3所示

(2)由图2-8-3可知:

①短语:S、a、(a)、S,(a)、(S,(a));

②直接短语:a、S;

③句柄:S;

④素短语:素短语可由图2-8-3中相邻终结符之间的优先关系求得,即;

因此素短语为a。

6、考虑文法G[T]:

T→TF|F

F→F↑P|P

P→(T)|i

证明TP↑(TF)是该文法的一个句型,并指出直接短语和句柄。

解答

首先构造TP↑(TF)的语法树如图2-8-4所示。

由图2-8-4可知,TP↑(TF)是文法G[T]的一个句型。

直接短语有两个,即P和TF;句柄为P。

一、单项选择题

1、词法分析所依据的是 。

a 语义规则 b 构词规则 c 语法规则 d 等价变换规则

2、词法分析器的输出结果是 。

a 单词的种别编码 b 单词在符号表中的位置

c 单词的种别编码和自身值 d 单词自身值

3、正规式M1和M2等价是指 。

a M1和M2的状态数相等 b M1和M2的有向弧条数相等

c M1和M2所识别的语言集相等 d M1和M2状态数和有向弧条数相等

4、状态转换图(见图3-6-1)接受的字集为 。

a 以 0开头的二进制数组成的集合 b 以0结尾的二进制数组成的集合

c 含奇数个0的二进制数组成的集合 d 含偶数个0的二进制数组成的集合

5、词法分析器作为独立的阶段使整个编译程序结构更加简洁、明确,因此, 。

a 词法分析器应作为独立的一遍 b 词法分析器作为子程序较好

c 词法分析器分解为多个过程,由语法分析器选择使用 d 词法分析器并不作为一个独立的阶段

解答 1、b 2、c 3、c 4、d 5、b

二、多项选择题

1、在词法分析中,能识别出 。

a 基本字 b 四元式 c 运算符

d 逆波兰式 e 常数

2、令∑={a,b},则∑上所有以b开头,后跟若干个ab的字的全体对应的正规式为 。

a b(ab) b b(ab)+ c(ba)b

d (ba)+b e b(a|b)

解答 1、a、c、e 2、a、b、d

三、填空题

1、确定有限自动机DFA是 的一个特例。

2、若二个正规式所表示的 相同,则认为二者是等价的。

3、一个字集是正规的,当且仅当它可由 所 。

解答 1、NFA 2、正规集 3、DFA(NFA)所识别

四、判断题

1、一个有限状态自动机中,有且仅有一个唯一终态。 ( )

2、设r和s分别是正规式,则有L(r|s)=L(r)|L(s)。 ( )

3、自动机M和M′的状态数不同,则二者必不等价。 ( )

4、确定的自动机以及不确定的自动机都能正确地识别正规集。 ( )

5、对任意一个右线性文法G,都存在一个NFA M,满足L(G)=L(M)。 ( )

6、对任意一个右线性文法G,都存在一个DFA M,满足L(G)=L(M)。 ( )

7、对任何正规表达式e,都存在一个NFA M,满足L(G)=L(e)。 ( )

8、对任何正规表达式e,都存在一个DFA M,满足L(G)=L(e)。 ( )

解答 1 、2、3、错 4、5、6、7、8、正确

五、基本题

1、设M=({x,y}, {a,b}, f,x,{y})为一非确定的有限自动机,其中f定义如下:

f(x,a)={x,y} f(x,b)={y}

f(y,a)=φ f(y,b)={x,y}

试构造相应的确定有限自动机M′。

解答:对照自动机的定义M=(S,Σ,f,S0,Z),由f的定义可知f(x,a)、f(y,b)均为多值函数,所以是一非确定有限自动机,先画出NFA M相应的状态图,如图3-6-2所示。

用子集法构造状态转换矩阵表3-6-3所示。

I Ia Ib

{x} {x,y} {y}

{y} — {x,y}

{x,y} {x,y} {x,y}

将转换矩阵中的所有子集重新命名而形成表3-6-4所示的状态转换矩阵。

表3-6-4 状态转换矩阵

a b

0 2 1

1 — 2

2 2 2

即得到M′=({0,1,2}, {a,b}, f,0, {1,2}),其状态转换图如图3-6-5所示。

将图3-6-5的DFA M′最小化。首先,将M′的状态分成终态组{1,2}与非终态组{0};其次,考察{1,2}。由于{1,2}a={1,2}b={2}⊂{1,2},所以不再将其划分了,也即整个划分只有两组{0},{1,2}:令状态1代表{1,2},即把原来到达2的弧都导向1,并删除状态2。最后,得到如图3-6-6所示化简DFA M′。

2、对给定正规式b(d|ad)(b|ab)+,构造其NFA M;

解答:首先用A+=AA改造正规式得:b(d|ad)(b|ab)(b|ab);其次,构造该正规式的NFA M,如图3-6-7所示。

求采纳为满意回答。

*** 作系统本就是软件,当然不可能是硬件做的,只是说 *** 作系统基于硬件,系统最开始只能做数据运算,比如加减法。。

下面是网上的解释

原始的计算机就是计算器,利用齿轮即可完成。但我理解现代计算机关键是有“程序自动存储运算”的功能(其实,这个东西齿轮应该也可以完成。古代有一个人的理想好像就是造这个东东,但没有成功,前些年,好像是英国政府悬赏,最终帮助这个古人了却了心愿。记得不太清楚了)。至于齿轮升级到继电器、电子管、晶体管,集成电路,无非是器件的更替,促进了性能的提高、高级功能的实现而已。可想而知,构想多么重要。

计算机没程序的时代,就是计算器时代。即使早期的计算机,也可以通过各种原始方法输入程序,顺序执行。比如穿孔什么的。

你不要狭隘地理解“计算机语言”。当计算机的硬件完成后,它自然(硬件就是这么设计的,学过数字电路很好理解)会根据程序指令输入处理一些事情。不存在不能识别语言的阶段。当然,以后人为了编程效率而发明高级语言,是必须要通过中介——编译程序(第一个编译程序本身多半靠人工翻译)将其翻译成机器能识别的基础指令。

编译器

编译器,是将便于人编写,阅读,维护的高级计算机语言翻译为计算机能识别,运行的低级机器语言的程序。编译器将源程序(Source program)作为输入,翻译产生使用目标语言(Target language)的等价程序。源程序一般为高级语言(High-level language),如Pascal,C++等,而目标语言则是汇编语言或目标机器的目标代码(Object code),有时也称作机器代码(Machine code)。

一个现代编译器的主要工作流程如下:

源程序(source code)→预处理器(preprocessor)→编译器(compiler)→汇编程序(assembler)→目标程序(object code)→连接器(链接器,Linker)→可执行程序(executables)

目录 [隐藏]

1 工作原理

2 编译器种类

3 预处理器(preprocessor)

4 编译器前端(frontend)

5 编译器后端(backend)

6 编译语言与解释语言对比

7 历史

8 参见

工作原理

翻译是从源代码(通常为高级语言)到能直接被计算机或虚拟机执行的目标代码(通常为低级语言或机器言)。然而,也存在从低级语言到高级语言的编译器,这类编译器中用来从由高级语言生成的低级语言代码重新生成高级语言代码的又被叫做反编译器。也有从一种高级语言生成另一种高级语言的编译器,或者生成一种需要进一步处理的的中间代码的编译器(又叫级联)。

典型的编译器输出是由包含入口点的名字和地址以及外部调用(到不在这个目标文件中的函数调用)的机器代码所组成的目标文件。一组目标文件,不必是同一编译器产生,但使用的编译器必需采用同样的输出格式,可以链接在一起并生成可以由用户直接执行的可执行程序。

编译器种类

编译器可以生成用来在与编译器本身所在的计算机和 *** 作系统(平台)相同的环境下运行的目标代码,这种编译器又叫做“本地”编译器。另外,编译器也可以生成用来在其它平台上运行的目标代码,这种编译器又叫做交叉编译器。交叉编译器在生成新的硬件平台时非常有用。“源码到源码编译器”是指用一种高级语言作为输入,输出也是高级语言的编译器。例如: 自动并行化编译器经常采用一种高级语言作为输入,转换其中的代码,并用并行代码注释对它进行注释(如OpenMP)或者用语言构造进行注释(如FORTRAN的DOALL指令)。

预处理器(preprocessor)

作用是通过代入预定义等程序段将源程序补充完整。

编译器前端(frontend)

前端主要负责解析(parse)输入的源程序,由词法分析器和语法分析器协同工作。词法分析器负责把源程序中的‘单词’(Token)找出来,语法分析器把这些分散的单词按预先定义好的语法组装成有意义的表达式,语句 ,函数等等。 例如“a = b + c;”前端词法分析器看到的是“a, =, b , +, c;”,语法分析器按定义的语法,先把他们组装成表达式“b + c”,再组装成“a = b + c”的语句。 前端还负责语义(semantic checking)的检查,例如检测参与运算的变量是否是同一类型的,简单的错误处理。最终的结果常常是一个抽象的语法树(abstract syntax tree,或 AST),这样后端可以在此基础上进一步优化,处理。

编译器后端(backend)

编译器后端主要负责分析,优化中间代码(Intermediate representation)以及生成机器代码(Code Generation)。

一般说来所有的编译器分析,优化,变型都可以分成两大类: 函数内(intraprocedural)还是函数之间(interprocedural)进行。很明显,函数间的分析,优化更准确,但需要更长的时间来完成。

编译器分析(compiler analysis)的对象是前端生成并传递过来的中间代码,现代的优化型编译器(optimizing compiler)常常用好几种层次的中间代码来表示程序,高层的中间代码(high level IR)接近输入的源程序的格式,与输入语言相关(language dependent),包含更多的全局性的信息,和源程序的结构;中层的中间代码(middle level IR)与输入语言无关,低层的中间代码(Low level IR)与机器语言类似。 不同的分析,优化发生在最适合的那一层中间代码上。

常见的编译分析有函数调用树(call tree),控制流程图(Control flow graph),以及在此基础上的 变量定义-使用,使用-定义链(define-use/use-define or u-d/d-u chain),变量别名分析(alias analysis),指针分析(pointer analysis),数据依赖分析(data dependence analysis)等等。

上述的程序分析结果是编译器优化(compiler optimization)和程序变形(compiler transformation)的前提条件。常见的优化和变新有:函数内嵌(inlining),无用代码删除(Dead code elimination),标准化循环结构(loop normalization),循环体展开(loop unrolling),循环体合并,分裂(loop fusion,loop fission),数组填充(array padding),等等。 优化和变形的目的是减少代码的长度,提高内存(memory),缓存(cache)的使用率,减少读写磁盘,访问网络数据的频率。更高级的优化甚至可以把序列化的代码(serial code)变成并行运算,多线程的代码(parallelized,multi-threaded code)。

机器代码的生成是优化变型后的中间代码转换成机器指令的过程。现代编译器主要采用生成汇编代码(assembly code)的策略,而不直接生成二进制的目标代码(binary object code)。即使在代码生成阶段,高级编译器仍然要做很多分析,优化,变形的工作。例如如何分配寄存器(register allocatioin),如何选择合适的机器指令(instruction selection),如何合并几句代码成一句等等。

编译语言与解释语言对比

许多人将高级程序语言分为两类: 编译型语言 和 解释型语言 。然而,实际上,这些语言中的大多数既可用编译型实现也可用解释型实现,分类实际上反映的是那种语言常见的实现方式。(但是,某些解释型语言,很难用编译型实现。比如那些允许 在线代码更改 的解释型语言。)

历史

上世纪50年代,IBM的John Backus带领一个研究小组对FORTRAN语言及其编译器进行开发。但由于当时人们对编译理论了解不多,开发工作变得既复杂又艰苦。与此同时,Noam Chomsky开始了他对自然语言结构的研究。他的发现最终使得编译器的结构异常简单,甚至还带有了一些自动化。Chomsky的研究导致了根据语言文法的难易程度以及识别它们所需要的算法来对语言分类。正如现在所称的Chomsky架构(Chomsky Hierarchy),它包括了文法的四个层次:0型文法、1型文法、2型文法和3型文法,且其中的每一个都是其前者的特殊情况。2型文法(或上下文无关文法)被证明是程序设计语言中最有用的,而且今天它已代表着程序设计语言结构的标准方式。分析问题(parsing problem,用于上下文无关文法识别的有效算法)的研究是在60年代和70年代,它相当完善的解决了这个问题。现在它已是编译原理中的一个标准部分。

有限状态自动机(Finite Automaton)和正则表达式(Regular Expression)同上下文无关文法紧密相关,它们与Chomsky的3型文法相对应。对它们的研究与Chomsky的研究几乎同时开始,并且引出了表示程序设计语言的单词的符号方式。

人们接着又深化了生成有效目标代码的方法,这就是最初的编译器,它们被一直使用至今。人们通常将其称为优化技术(Optimization Technique),但因其从未真正地得到过被优化了的目标代码而仅仅改进了它的有效性,因此实际上应称作代码改进技术(Code Improvement Technique)。

当分析问题变得好懂起来时,人们就在开发程序上花费了很大的功夫来研究这一部分的编译器自动构造。这些程序最初被称为编译器的编译器(Compiler-compiler),但更确切地应称为分析程序生成器(Parser Generator),这是因为它们仅仅能够自动处理编译的一部分。这些程序中最著名的是Yacc(Yet Another Compiler-compiler),它是由Steve Johnson在1975年为Unix系统编写的。类似的,有限状态自动机的研究也发展了一种称为扫描程序生成器(Scanner Generator)的工具,Lex(与Yacc同时,由Mike Lesk为Unix系统开发)是这其中的佼佼者。

在70年代后期和80年代早期,大量的项目都贯注于编译器其它部分的生成自动化,这其中就包括了代码生成。这些尝试并未取得多少成功,这大概是因为 *** 作太复杂而人们又对其不甚了解。

编译器设计最近的发展包括:首先,编译器包括了更加复杂算法的应用程序它用于推断或简化程序中的信息;这又与更为复杂的程序设计语言的发展结合在一起。其中典型的有用于函数语言编译的Hindley-Milner类型检查的统一算法。其次,编译器已越来越成为基于窗口的交互开发环境(Interactive Development Environment,IDE)的一部分,它包括了编辑器、连接程序、调试程序以及项目管理程序。这样的IDE标准并没有多少,但是对标准的窗口环境进行开发已成为方向。另一方面,尽管近年来在编译原理领域进行了大量的研究,但是基本的编译器设计原理在近20年中都没有多大的改变,它现在正迅速地成为计算机科学课程中的中心环节。

在九十年代,作为GNU项目或其它开放源代码项目的一部分,许多免费编译器和编译器开发工具被开发出来。这些工具可用来编译所有的计算机程序语言。它们中的一些项目被认为是高质量的,而且对现代编译理论感性趣的人可以很容易的得到它们的免费源代码。

大约在1999年,SGI公布了他们的一个工业化的并行化优化编译器Pro64的源代码,后被全世界多个编译器研究小组用来做研究平台,并命名为Open64。Open64的设计结构好,分析优化全面,是编译器高级研究的理想平台。

编译器是一种特殊的程序,它可以把以特定编程语言写成的程序变为机器可以运行的机器码。我们把一个程序写好,这时我们利用的环境是文本编辑器。这时我程序把程序称为源程序。在此以后程序员可以运行相应的编译器,通过指定需要编译的文件的名称就可以把相应的源文件(通过一个复杂的过程)转化为机器码了。

编译器工作方法

首先编译器进行语法分析,也就是要把那些字符串分离出来。然后进行语义分析,就是把各个由语法分析分析出的语法单元的意义搞清楚。最后生成的是目标文件,我们也称为obj文件。再经过链接器的链接就可以生成最后的可执行代码了。有些时候我们需要把多个文件产生的目标文件进行链接,产生最后的代码。我们把一过程称为交叉链接。

编译阶段和JIT编译阶段

运行时必须经过两个阶段(如下图所示)

1)编译阶段:

在编译使用NET 框架创建的代码时,不是立即创建 *** 作系统特定的本机代码,而是把代码编译为微软中间语言(Microsoft Intermediate Language,MSIL)代码,这些MSIL代码不专用于任何一种 *** 作系统,也不专用于任何一种语言,有些类似于JAVA的字节码。C#及其他NET语言,如VBNET在编译阶段都编译为这种语言。

2)JIT编译阶段

因为代码在编译阶段没有直接编译成本机代码,所以在执行应用程序时,必须完成更多的工作,这就是Just In Time(JIT)编译器的任务。JIT把MSIL编译为专用于某种 *** 作系统和目标机器结构的本机代码,只有这样, *** 作系统才能执行应用程序。这里编泽器的名称Just In Time,反映了MSIL仅在需要时才编译的特性。

以上就是关于典型的编译器可以划分成几个逻辑阶段全部的内容,包括:典型的编译器可以划分成几个逻辑阶段、编译原理题目、在刚开始只有硬件没有软件的情况下, *** 作系统是用硬件做出来的吗等相关内容解答,如果想了解更多相关内容,可以关注我们,你们的支持是我们更新的动力!

欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/zz/9479617.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2023-04-28
下一篇 2023-04-28

发表评论

登录后才能评论

评论列表(0条)

保存