《程序设计语言概念》 第六章 类型系统和类型推测
很多程序设计语言将数据和计算包装成类型(type)的集合(collection)。
6.1 程序设计中的类型
数据结构、函数、对象、通道和控制线程这些都是可计算性结构,都可以有类型。
类型主要有以下作用:
- 命名和组织概念
- 确保内存中的比特序列被正确理解
- 向编译器提供程序中操作的数据信息
1. 程序的组织和文档
类型实际上起到了描述程序设计意图的文档的作用。相对注释,类型会被编译器检查,而注释不会被检查,一旦写错了就不会得到出错警告或提示。
2. 类型错误
包括硬件错误、语义错误。
如果一组被认为是在表示一种类型的值的比特序列被当做另一种类型使用就是一种类型错误。
3. 类型与优化
类型信息可以被用于各种优化。
如果在编译时知道某种操作的类型,那么这种操作的编译结果的执行效率就可以更高。
6.2 类型安全和类型检查
1. 类型安全
如果一种语言的程序不能违反类型差别,那么这种语言就是类型安全的。
安全性 | 语言 | 解释 |
不安全 | C/C++ | 支持类型转换,指针算术运算 |
基本安全 | Pascal | 明确的内存释放;然而,存在悬吊指针 |
安全 | Lisp, ML, Smalltalk, Java | 完备的类型检查 |
悬吊指针:指向没有被申请的内存区域的指针。比如一个指针p原本指向一个整数,在释放了p指向的内存后,这片区域可能被申请来存储指向别的类型的值,但这片区域仍然能够通过p访问,并且被当做整型区域访问,这就违反了类型安全。
delete p;
p=NULL; //这一句就是为了避免p成为悬吊指针。
2. 编译时和运行时类型检查
类型检查的形式 | 优点 | 缺点 |
运行时 | 杜绝类型错误 | 降低程序执行速度 |
编译时 | 杜绝类型错误 避免运行时检查引入的开销 在程序执行之前找到类型错误 | 因为测试时保守的从而限制编程 |
现在大多数语言实际上同时使用编译时和运行时类型检查。
6.3 类型推测