温编译之故 知C语言之新

  又学了一遍“编译原理”课程,文法、词法、语法、语义、优化……这次一串,可以在理解新技术的同时,利用温习老技术的悠闲中思考在C语言中的实例与联系,或有心得。

 

1. 类型的等价


  C语言语义分析允许此类赋值,编译器认为time_t和int为同一类型,则不会出现Warning;然而从语义分析,typedef将int特华为time_t同时赋予了不同于一般int的语义信息,即表征了某类客观对象,则不应进行这样泛化的赋值。看来这种“特化的int不是int”与面向对象“A的子类仍是A”有些相左。在某些PASCAL编译器中这种自然赋值就会被检查出来。


  同样的道理,类型struct A与struct B为不同类型,而这次C编译器不允许此类赋值。
判定类型是否相同的策略,包括名字相同、内容相同、位置相同等,严格性依次递增,C语言属于限制比较小的类型,毕竟它的理念是“程序员总是对的”。

 

2. 符号表的建立

  合法变量名字由字母、数字几下划线组成,但不能数字开头。则仅一个下划线“_”可以作为名字吗?
可以,因为这不影响词法分析有穷自动机(DFA)的工作。DFA通过符号首字判断是变量名(函数名)还是常量或其它。若是前者则置入符号表。
  那这个工作何时启动?一种想法是在遇到语句块首符号“{”开始。因此函数变量声明需在首部进行。尽管没有PASCAL的嵌套函数规则,C语言也同样存在嵌套变量,一个if语句块、或者就是函数内部的顺序语句块。

 

3. 指针运算可能影响编译优化

  编译器进行寄存器优化,其中算法确定变量何时写回内存。插入一条指针运算语句需让编译器知晓是否存在“同名变量”,否则优化结果降低。一个*p已经需要一番周折了,何况p要++,指向方向又不好确定。如果还是参数传来的p,更是难以琢磨了。由此观之,是不是要节制的使用指针了。

 

4. 符号表内变量大小

  符号表内的变量大小体现在在编译时一个长度变量length的递增数显现。

  对于类似结构Vail的空struct,约定sizeof struct Vail为1,通常的理解为不至出现其数组vs[]和指针*pv的怪异性质。在符号表生成中,不会出现length递增为0的情况。

  不过在gcc 4.2编译时,有这样的结果:

sizeof(struct Vail)=0, sizeof(vs)=0, pv=pv+1。

  由此观之,只要逻辑上合理,不同的编译原则都是可以接受的。

 

5. (C++)Exception处理
  Exception是C++等面向对象语言的特点。据说Cfont使用C语言模仿C++时在Exception处理时遇到困难,那现代C++编译器是如何实现的?猜想用中断方式,又不大可能。大凡用一句一句检查的方法。记得在一个注重效率的嵌入式程序中,一个高频率执行的try块中几十条语句,每条都有可能抛出关心或不关心的Exception。现在想来,是否应该进行重写,而损失了程序的可读性。

                                              From http://blog.csdn.net/stoneandice

参考文献

 Alfred V.Aho, Ravi Sethi, Jeffrey D.Ullman. Compilers: Principles, Techniques and Tools(2nd). Pearson Education, Inc 2006

Compiler Principles(2nd)

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值