AutoCAD 3DMAX C语言 Pro/E UG JAVA编程 PHP编程 Maya动画 Matlab应用 Android
Photoshop Word Excel flash VB编程 VC编程 Coreldraw SolidWorks A Designer Unity3D
 首页 > C++

C++箴言:理解隐式接口和编译期多态

51自学网 http://www.wanshiok.com

  由一个 constructor(构造函数),一个 destructor(析构函数),以及函数 size,normalize 和 swap 组成,再加上 parameter types(参数类型),return types(返回类型)和这些函数的 constnesses(常量性)。(它也包括 compiler-generated(编译器生成)的 copy constructor(拷贝构造函数)和 copy assignment operator(拷贝赋值运算符)——参见《C++箴言:了解C++偷偷加上和调用了什么》)它还可能包含 typedefs,还有,如果你胆大包天敢于违背让 data members(数据成员)private(私有)的建议,即使在这种情况下,这些 data members(数据成员)也不是。

  一个 implicit interface(隐式接口)有很大不同。它不是基于 function signatures(函数识别特征)的。它是由 valid expressions(合法表达式)组成的。再看一下在 doProcessing template 开始处的条件:

template<typename T>
void doProcessing(T& w)
{
if (w.size() > 10 && w != someNastyWidget) {
...

  对于 T(w 的类型)的 implicit interface(隐式接口)看起来有如下这些约束:

  ·它必须提供一个名为 size 的返回一个正数值的 member function(成员函数)。

  ·它必须支持一个用于比较两个类型 T 的对象的 operator!= 函数。(这里,我们假定 someNastyWidget 的类型为 T。)

  由于 operator overloading(运算符重载)的可能性,这两个约束都不必满足。是的,T 必须支持一个 size member function(成员函数),值得提及的是虽然这个函数可以是从一个 base class(基类)继承来的。但是这个 member function(成员函数)不需要返回一个整数类型。它甚至不需要返回一个数值类型。对于这种情况,它甚至不需要返回一个定义了 operator> 的类型!它要做的全部就是返回类型 X 的一个 object(对象),有一个 operator> 可以用一个类型为 X 的 object(对象)和一个 int(因为 10 为 int 类型)来调用。这个 operator> 不需要取得一个类型 X 的参数,因为它可以取得一个类型 Y 的参数,只要在类型 X 的 objects(对象)和类型 Y 的 objects(对象)之间有一个 implicit conversion(隐式转型)就可以了!

  类似地,T 支持 operator!= 也是没有必要的,因为如果 operator!= 取得一个类型 X 的 objects(对象)和一个类型 Y 的 objects(对象)是可接受的一样。只要 T 能转型为 X,而 someNastyWidget 的类型能够转型为 Y,对 operator!= 的调用就是合法的。

  (一个旁注:此处的分析没有考虑 operator&& 被重载的可能性,这会将上面的表达式的含义从与转换到某些大概完全不同的东西。)

  第一次考虑 implicit interfaces(隐式接口)的时候,大多数人都会头疼,但是他们真的不需要阿司匹林。implicit interfaces(隐式接口)简单地由一套 valid expressions(合法表达式)构成。这些表达式自身看起来可能很复杂,但是它们施加的约束通常是简单易懂的。例如,给出这个条件,

if (w.size() > 10 && w != someNastyWidget) ...

  关于 functions size,operator>,operator&& 或 operator!= 上的约束很难说出更多的东西,但是要识别出整个表达式的约束是非常简单的。一个 if 语句的条件部分必须是一个 boolean expression(布尔表达式),所以不管 "w.size() > 10 && w != someNastyWidget" 所产生的类型涉及到的精确类型,它必须与 bool 兼容。这就是 template(模板)doProcessing 施加于它的 type parameter(类型参数)T 之上的 implicit interface(隐式接口)的一部分。被 doProcessing 需要的 interface(接口)的其余部分是 copy constructor(拷贝构造函数),normalize 和 swap 的调用对于类型 T 的 objects(对象)来说必须是合法的。

  implicit interface(隐式接口)对 template(模板)的 parameters(参数)施加的影响正像 explicit interfaces(显式接口)对一个 class(类)的 objects(对象)施加的影响,而且这两者都在编译期间被检查。正像你不能用与它的 class(类)提供的 explicit interface(显式接口)矛盾的方法使用 object(对象)(代码无法编译)一样,除非一个 object(对象)支持 template(模板)所需要的 implicit interface(隐式接口),否则你就不能在一个 template(模板)中试图使用这个 object(对象)(代码还是无法编译)。

  Things to Remember

  ·classes(类)和 templates(模板)都支持 interfaces(接口)和 polymorphism(多态)。

  ·对于 classes(类),interfaces(接口)是 explicit(显式)的并以 function signatures(函数识别特征)为中心的。polymorphism(多态性)通过 virtual functions(虚拟函数)出现在运行期。

  ·对于 template parameters(模板参数),interfaces(接口)是 implicit(隐式)的并基于 valid expressions(合法表达式)。polymorphism(多态性)通过 template instantiation(模板实例化)和 function overloading resolution(函数重载解析)出现在编译期。

 
 

上一篇:C++程序设计从零开始之语句  下一篇:C++对象布局及多态之虚成员函数调用