C++ 对象模型 第一章 关于对象

补充:

全局变量 (所有文件可见)
静态全局变量(当前文件可见)
局部变量(当前Scope可见)

类的继承关系中的虚继承(virtual)就是共享的意思

纯虚函数:只能用于继承,它的实现留给该基类的派生类去做。

内联函数(inline function)在计算机中,内联函数是一种程序语言结构,用来建议编译器对一些特殊函数进行内联扩展;也就是说建议编译器将指定的函数体插入并取代每一处每一处调用该函数的地方,从而节省了每次调用函数带来的额外时间开支。


第一章  关于对象

1)在c语言中,“数据”和“处理数据的操作(函数)”是分开声明的,也就是说,语言本身没有支持“数据和函数”之间的关联,我们把这种程序方法称为程序性的。


2)point3d采用独立的ADT实现
point3d(float x=0.0,float y=0.0,float z=0.0):_x(x),_y(y),_z(z){}


   point3d采用一个3层的class层次结构完成
point3d(float x=0.0,float y=0.0,float z=0.0):point2d(x,y),_z(z){}


3)加上封装后的布局成本
class point3d没有增加任何成本:三个data members直接内含在每一个class object之中,就像struct c一样。而member functions虽然含在class声明之内,却不出现在object之中。  每一个non-inline成员函数只会诞生一个函数实例。每一个拥有“零个或一个定义”的inline 函数则会在每一个使用者身上产生一个函数实例。

可以看到类的封装性质,并没有给它带来任何空间或执行期的不良后果。c++在布局以及存取时间上的主要额外负担是由virtual机制引起的,主要包括:①virtual function机制:用以支持一个有效率的“执行器绑定”② virtual base class机制:用以实现“多次出现在继承体系中的base class,有一个单一共享的实例”//虚基类只调用一次构造函数


4)在c++中,类数据成员有两种类型:static和non-static,类的成员函数有三种:static、non-static、virtual。


5)c++对象模式 
①简单对象模型:每一个slot指向一个member(类数据成员或类成员函数),members按其声明顺序,各被指定一个slot。在该模型下,object中的不是members本身,而是指向members的指针
②表格驱动对象模型:每个对象有两个slot,指向两张表,一张是数据成员表,另一张是类成员函数。
③c++对象模型:Nonstatic data members配置于每一个类对象中,static data member被置于类对象之外。 static 和nonstatic成员函数也被置于类对象之外。virtual fucntion则以两个步骤支持:1、每个class产生出一堆指向virtual function的指针,放在表格之中。这个表格被称为virtual table(vtbl)2、每个类对象中有一个指针(vptr),指向相关的virtual table。


6)(*px->vtbl[2])(px);等价于(*(px->vtbl[2]))(px);


7) int (*pf)(1024); //调用
   int (*pq)(); //声明


8)以下两个声明的矛盾
static int foo; 
extern int foo;
static 表示foo变量只能在当前文件使用,而extern表示在别的文件中定义在当前文件中使用。这是矛盾的。


9)下面的代码是不合法的:
template <truct Type>
struct m2{
Type a;
};

而将struct改为class就合法化了。


10)c++程序设计模型直接支持三种程序设计范式:
①procedural model
②abstract data type model,此模型所谓的抽象是和一组表达式(public接口)一起提供的。
③object-oriented model
OO范式中,程序员需要处理一个未知实例,原则上被指定的object的真实类型在每一个特定执行点之前是无法解析的。在c++中,只有通过pointers和references的操作才能够完成。
ADT范式中,程序员处理的是一个拥有固定而单一类型的实例,它在编译时期就已经完全定义好了。


Libara_materials *px=retrieve_some_material();
Libara_materials &rx=*px;
Libara_materials dx=*px;
绝对没有办法说出px或rx究竟是何种类型的对象,只能说它要么好似一个Libara_materials 对象,要么是后者的一个子对象。而dx只能是Libara_materials类型的对象。


11)虽然可以直接或间接处理继承体系中的一个base class object,但只有通过pointer或reference的间接处理,才支持OO程序设计所需要的多态性质。

12)c++的多态性只存在于一个个的public class体系中
c++支持多态的方法:
①经由一组隐式的转换操作 例如把一个derived class指针转换为  一个指向pubic base typede 指针
shape *ps=new circle();
②经由virtual function机制:ps->rotate();
③经由dynamic_cast和typeid运算符:
if(circle *pc=dynamic_cast<circle *>(ps))
多态的主要用途是经由一个共同的接口来影响类型的封装,这个接口通常定义在一个抽象的base class中

static_cast:静态转换,static_cast可能意味着冒险(比如变换时类似于强制转换一样丢失信息)。但是在一个类层次中没有虚函数或者我们确定有其他允许我们安全向下映射的信息则后者static_cast更快一些。
dynamic_cast:动态转换,试探映射,成本较高

13)类对象的空间计算
需要多少内存才能够表现一个class object?
①nonstatic data members 总和大小
②加上任何由于alignment的需求而填补上去的空间。注:alingment就是将数值调整到某数的整数倍
③加上支持virtual而产生的额外负担


14)
OO:object Oriented 面向对象
OB:object Base基于对象(String 类型)
一个OB设计可能比一个OO设计速度更快而且空间更紧凑。


15)

假设Bear继承自ZooAnimal 。那么一个Bear指针和一个ZooAnimal指针有什么不同?

Bear b;

ZooAnimal *pz=&b;

Bear *pb=&b;


它们都指向Bear Object的第一个byte.其间差别是,pb所涵盖的地址包含整个Bear object,而pz所涵盖的地址只包含Bear object中的ZooAnimal subobject.

除了ZooAnimal subobject中出现的members,你不能够使用pz来直接处理Bear的任何members。唯一例外是通过virtual机制:


当用pz去调用Bear类中非继承的数据成员时,操作时不合法的。

如:pz->cell_block;


可以经由一个现实的downcast操作

如:(static_cast<Bear*>(pz))->cell_block;


也可以经由一个run-time operation,但是成本较高


如:Bear * pb2=dynamic_cast<Bear*>(pz);

pb2->cell_block;












评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值