C# 1的核心基础之二——类型系统
C# 1的核心基础之二——类型系统
C#的类型特征
C# 1的类型系统是静态的、显式的和安全的。大多数情况下说C#是“强类型”就是指静态类型。
静态类型和动态类型
静态类型:每个变量都有一个特定的类型,并且该类型在编译时是已知的。
动态类型:编译器不能执行类型检查,相反会试图采取一种合适的方式来理解引用值的给定表达式。
C#从1到3都是完全静态的语言。C# 4引入了动态类型,然而大多数代码仍然是静态类型的。显式类型和隐式类型
这两个概念只有在静态类型语言中才有意义——因为类型在编译时都是已知的。
显式类型:每个变量的类型必须在声明中显式指明。
隐式类型:允许编译器根据变量用途来推断变量的类型。类型安全与类型不安全
有些语言(尤其是C和C++)允许做一些“不正当”的事,号称功能强大,但大多数情况下都“搬起石头砸自己的脚”。
类型安全:强制类型转换时,编译器会检查转换是否可行,不行会触发编译时错误。如果理论上可行,执行时发现不正确,CLR也会抛出异常。
类型不安全:允许在完全不相干的类型将进行强制类型转换,容易造成严重的后果。
C# 1类型系统的限制
集合,强和弱
.NET 1.1内建的三种集合类型:- 数组——强类型——内建到语言和运行时中;
- System.Collections命名空间——弱类型——无法得到编译时的类型安全;
- System.Collections.Specialized命名空间——强类型集合——为每种类型创建新的强类型集合不是很理想。
缺乏协变的返回类型
协变->“和谐的变”->“很自然的变化”->string到object:协变;
逆变->“逆常的变”->“不正常的变化”->object到string:逆变。
由于缺乏协变的返回类型,所以不得不在实现接口时选择实现一个返回指定类型的方法,然后显式实现接口来调用它——虽然可行,但是一点都不优雅。
其实也缺乏参数类型的逆变性,对于接口解决方案是一样的,对于虚方法,解决方案是进行普通的方法重载——确实很烦人。
总结
C# 1的类型特征:
- 静态类型的——编译器知道你使用那些类型;
- 显式的——必须告诉编译器变量的类型是什么;
- 安全的——除非存在真是的转换关系,否则不能将一种类型当另一种类型使用;
- 集合不是强类型的,除非针对特定元素使用大量的重复代码;
- 方法覆盖和接口实现不允许协变性/逆变性。