指针的类型
创新互联公司网站建设提供从项目策划、软件开发,软件安全维护、网站优化(SEO)、网站分析、效果评估等整套的建站服务,主营业务为成都网站设计、网站制作、外贸营销网站建设,重庆App定制开发以传统方式定制建设网站,并提供域名空间备案等一条龙服务,秉承以专业、用心的态度为用户提供真诚的服务。创新互联公司深信只要达到每一位用户的要求,就会得到认可,从而选择与我们长期合作。这样,我们也可以走得更远!不同类型的指针,从内存需求的观点来说,没有什么不同!他们三个都需要足够的内存来繁殖一个机器地址,“指向不同类型之各指针”之间的差异,既不在其指针表示法不同,也不再其内容(代表一个地址)不同,而是在其所寻址出来的对象类型不同。也就是说,“指针类型”会导致编译器如何解释某个特定地址中的内存内容及其大小
1、 一个指向地址1000的整数地址,在32位机器上,将涵盖地址空间1000~1003
2、 那么,一个指向地址1000而类型为void*的指针,将涵盖怎样的地址空间呢?这个不知道,这就是为什么一个类型为void*的指针只能够含有一个地址,而不能通过它操作所指之对象的缘故。
其实转型是一种编译器指令,大部分情况下它并不改变一个指针所含的真正地址,它只影响“被指出之内存的大小和其内容”的解释方式。
Class ZooAnimal{
Public:
ZooAnimal();
Virtual~ZooAnimal();
Virtualvoid rotate();
Protected:
Intloc;
Stringname;
};
Class bear:public ZooAnimal
{
Public:
Bear();
~Bear()
Voidrotate();
Viratul void dance();
Protected:
Int cell_block;
};
但是考虑多态以后呢?加入Bear继承了ZooAnimal 同时是Public继承
Bear b;
ZooAnimal *pz = &b;
Bear* pb = &b;
他们每个都指向Bear对象的第一个字节,其间的差别是,pb所涵盖的地址包含整个Bear对象,而pz所涵盖的地址只包含Bear对象中的ZooAnimal子对象
除了在ZooAnimal中出现的成员,你不能够实用pz来直接处理Bear的任何成员。唯一例外的是通过virtual机制。
Pz->cell_block;
//不正确,cell_block不是ZooAnimal的一个成员,虽然我们知道pz当前指向一个Bear对象
((Bear*)pz)->cell_block;
//合法 经过一个明白的转型操作就没有问题
Pb->cell_block;
//合法 因为cell_block是Bear的一个成员
但是当我们写
Pz->rotate();时,(rotate是虚拟函数)pz的类型将在编译使其决定一下两点:
固定的可用接口,也就是说,pz只能够调用ZooAnimal的Public接口
该接口的访问级别(例如rotate()是ZooAnimal的一个public成员)
在每一个执行点,pz所指的对象类型可以决定rotate()所调用的实体,类型信息的封装并不是维护与pz之中,而是维护与link之中,此Link存在于对象的vptr和vptr所指的virtual table之间,在每一个virtual table中都有一个信息是type of info的信息
Bear b;
ZooAnimal za = b; //这样会引起切割
Za.rotate(); //调用ZooAnimal::rotate()
为什么rotate()所调用的是ZooAnimal实体而不是Bear实体?为什么za的vptr不指向Bear的virtual table
编译器在初始化以及赋值操作(将一个对象赋值给另一个对象)之间做了仲裁,编译器必须确保如果某个对象含有一个或一个以上的vptrs,那么vptrs的内容不会被基类对象初始化或改变
加入ZooAnimal->Bear->Panda 继承关系
ZooAnimal za;
ZooAnimal * pza;
Bear b;
Panda* pp = new Panda;
Pza = *b
将za或b的地址,或pp所含的内容(也是个地址)指定给pza,显然不是问题,一个指针或一个引用值所以支持多态,是因为它们并不引发内存中任何“与类型有关的内存委托操作”,会受到改变的只是它们所指向的内存的“大小和内容解释方式”而已。
所谓与类型有关的内存委托操作是指这个类型被编译所认识的大小,比如上面使用pz->cell_block.
大小和内容解释方式是在编译期间发生的,但是对于多态来说,是一个函数,但是函数是不依附于对象的,如果只要访问的对象中存在这个函数并且这个函数的访问级别可以达到,编译期间就可以实现,但是等到运行期间,如果发现这个函数是一个虚函数,这个时候在虚函数表中的第一个位置就是关于这个类型的所有信息,这个时候就会知道这个对象对应的真实类型是什么。需要分清这两点的差异
另外有需要云服务器可以了解下创新互联scvps.cn,海内外云服务器15元起步,三天无理由+7*72小时售后在线,公司持有idc许可证,提供“云服务器、裸金属服务器、高防服务器、香港服务器、美国服务器、虚拟主机、免备案服务器”等云主机租用服务以及企业上云的综合解决方案,具有“安全稳定、简单易用、服务可用性高、性价比高”等特点与优势,专为企业上云打造定制,能够满足用户丰富、多元化的应用场景需求。