文章目录
考前提醒
- 第一题:问(3)把转化关系先在草稿纸上列出来,主要算终点的时候不要把起点加进去。问(3)最小状态自动机要画图
- 第四题:问(1)我总是漏写,问(3)先把所有的移进规约并排列出来,再杠掉。所以每个空格留宽一点。
tips
- first集就是非终结符星推导得到的第一个终结符或者 的集合。当 , 我们才能说 。
- follow集就是非终结符后面可能出现的第一个终结符或结束符的集合。求follow集时,第一步 follow(S)={$}, S是开始符。
- predict集指使用该产生式推导得到的栈顶终结符(包括结束符),或继续星推导得到的栈顶终结符或结束符。
易错提醒
- DFA最小状态自动机化简:不可达状态就在表上面空着,别手残填多了
- 做题的时候把产生式中的 | 展开,防止看漏了
- LL(1)分析表和SLR分析表中都有对应 $ 的项
- 消除左公因子的时候别忘了有个 产生式
- 单位可能是字节,所以要乘4
语法制导SDD
- 区分继承属性和综合属性
- 如果可以画注释树的话,写SDD会更方便。
- 例子:中缀表达式->后缀表达式,in是继承属性,infix是综合属性。
gcc
空间存储组织
- (下面是大地址、上面是小地址)
- 小端编址(小对小、大对大)
过程调用
- 上面是栈顶
- old fp字段中保存了原寄存器的值,包括ebp基地址:esp 偏移指针。esp在高位2个字节,ebp在低位两个字节。
过程参数
- 从右往左进栈。下面是测试程序
void f ( int a, int b ) {
printf("%x %x",&a, &b);
return;
}
输出: 61ff10 61ff14 说明b先进栈
数组
数组和指针类型是不一样的,前者是array(int , n), 后者是 int *。
只不过在表达式中,编译程序把数组类型转换成指向第一个元素的指针。
表达式 | a的类型 |
---|---|
int a[4][3] | int [4][3] |
&a(上面的a) 或 int *a[4][3] | int (*)[4][3] |
int **a | int ** |
例0809
例0708
二义性
改造文法
例1:
- 左结合:让它只能往左拓展,
- 消除优先级(*优先):引入T承担*的任务。
例2:
- 例3:
改造文法:使[]优先级高于*,*优先级高于+。且+是左结合运算
注意,第三项[]中是E不是F,因为[]可以使优先级"清零"。
LR分析,改造分析表
例:
设定优先级如下:*的优先级大于+,且+是左结合的,则有
- 下一个符号为+时,我们应该将E+E归约为E
- 下一个符号为*时,我们应该移入*,期待移入下一个符号
DFA -> RE(个人总结)
有多个终止状态
先求出每个终止状态对应的RE, 再合并。
例:
- 以AC为终止的状态:(b|ab)*
- 以BD为终止的状态:(b|ab)*a
- RE: (b|ab)*(a| )