接口类型
分类索引:C# 语言和运行时剖析--前言
基本概念
一.什么是接口
- CLR中的接口定义:对一组方法进行了统一签名的类型。
- 从以上定义中可以看出,接口中可以包含的成员包括:
- 方法
- 属性(本质是方法)
- 事件(本质是方法)
二.为什么使用接口
使用接口是面向抽象编程和解耦合的重要方法。能够帮助实现五大基本OO原则的以下几条原则:
- 开放闭合原则,面向接口编程可以灵活的使用实现接口IA的类CB替换类CA,而不用修改CA去满足新的业务需求。
- 接口复用原则,可以灵活的使用一系列轻量的,不同关注点的接口在不同的业务场合,替换对类的直接引用。
- 依赖反转原则,高层模块不直接依赖底层模块的实现,两者都依赖抽象编程。
三.接口的修饰
- CLR要求将将接口方法标记为Public
- CLR要求将接口方法标记为virtual
-
- 如果没有将方法标记为virtual,CLR将自动将该方法标记为virtual和 sealed,这样,该方法就不能在派生类中重写。
- 如果显示的将接口方法标记为virtual,CLR将保持该方法的非密封状态,这样,该方法就可以在派生类中重写。
- 如果派生类需要重写该接口方法时,就需要在派生类中重新继承并实现该接口方法。
四.泛型接口
- 泛型接口提供了出色的编译时类型安全性。非泛型接口在支持多种类型时,往往只能通过object类型的传递和返回,不利于对类型的编译时检查。
- 泛型接口在处理接口时,装箱拆箱的几率要小得多。这个优点同第一个,因为不用可以使用强类型,不用将值类型转换为object。
- 类可以实现同一个接口若干次,只要每次使用不同的类型参数。例如,类CA可以同时实现 IComparable<int32>, Icomparable<string>.
- 提高了内部方法的可重用性。
接口实现
一.隐式和显示实现接口
在继承接口后,右键单击接口名,会出现实现接口与显示实现接口的命令菜单。两种方式的区别在于:
- 隐式实现接口方法是默认的接口实现方法,这个时候在实现接口的类CA中,重写了接口方法。
- 显示接口方法后,通过接口,例如IDispose.Dispose()方法时,会调用显示接口方法。
例如:Class CA = new Class();
(IDispose)CA.Dispose()
调用的就是显示实现接口方法。
二.实现多个具有相同方法名和签名的接口
加入类CA同时实现接口IA和IB,IA和IB中都具有对方法MethodA的定义,这个时候,就必须用显示实现接口来区分对两个接口方法的实现。
三.泛型接口的约束
使用where条件来对泛型接口的参数进行约束。优势在于:
- 将一个泛型参数约束为多个接口,如果约束为多个接口,则必须传递同时实现多个接口的类。
- 传递值类型的时候可以减少装箱操作。
最佳实践
一.设计基类和接口的时机选择
- 在设计时,如果体现了"IS-A"的关系,应该考虑使用基类。如果体现了"CAN-DO"的关系,应该考虑使用接口
- 一般来说,基类型更易于使用,代码重用性更高
- 基类型更能提供一致性的实现和版本控制。
- 在实践中,最好是两种方式共同使用,为自己定义的接口提供基类型的默认实现并支持衍生类型的扩展。
二.谨慎使用显示实现接口
- 显示实现接口比较容易在实践中产生混淆。因为不能直接从类型调用,而必须先将类型转化为接口后调用。
- 显示实现接口不支持派生类型调用。
三.在接口中的方法需要支持多种参数扩展时,尽量使用泛型接口
- 代码的复用性更高。
- 将同一类业务对象置于同一个接口下,代码的内聚性更好。
- 通过不同的参数,可以实现不同的扩展。
相关阅读