protectedInheritance.cpp
间接继承和书本描述不一致,书上说因为第一重继承变private,第二重继承才无法访问Base::i~是private,现实是提示Base::i是protected,好像跳过Private_derived类直接找基类了。
继承对基类的保护,还是普遍规律,只能越来越严,不能变松。
还有,标号不是限制派生类对基类成员(表达不清楚,是基类成员还是从基类继承过来的成员?)的访问,
原话:所有继承Base的类对Base中的成员具有相同的访问(指什么,成员?怎么理解恰当,派生类包括基类,所以这里的对基类访问指对派生类中包含的基类部分访问?)
标号是限制用户和派生类的派生类(也当作一种用户吧?)对派生类(从基类继承来的)成员的访问
//公用、私有和受保护的继承
#include<iostream>
class Base{
public:
void basemem();
protected:
int i;
};
//struct直接继承class?可以?还有默认访问级别不同,一个public,一个private,转换后不要忘了
struct Public_derived : public Base{
int use_base() { return i; }//顾名思义,使用一下base看看
};
struct Protected_derived : protected Base{
int use_base() { return i; }
};
struct Private_derived : private Base{
int use_base() { return i; }//也没问题,尽管private~~~private不是设给它的,是给用户和下一个派生类的
};
//下一层派生
struct Derived_from_Private : public Private_derived{
int use_base() { return i; }
//书上的注释,Base::i is private in Private_derived,
//实际错误提示:'int Base::i' is protected,可能说明直接以用户身份去Base里找了,是protected,如果间接找,这个提示费劲
};
struct Derived_from_Public : public Public_derived{
int use_base() { return i; }//可以访问,因为Base::i在Public_derived类中仍然是protected
};
int main(){
Base b;
Public_derived d1;
Protected_derived d3;
Private_derived d2;
b.basemem();//b对象,肯定能访问
d1.basemem();//对于d1对象,basemem()还是public
//d2.basemem();//basemem()是private,不能访问
//d3.basemem();//protected当然也不行了
}
接口继承与实现继承:
public派生的类与基类有相同的接口。在设计良好的层次中,public派生的类可以用在任何需要基类对象的地方。
非public派生的类不继承基类的接口,称为实现继承,(用基类做它的实现,但不用基类做接口)
using.cpp
经过测试,using的用法和书上差距很大~!!!!!!!!!!!!!!!!!!(mark)
base的protected,用private继承,结果过用using可以变成public~~~!!!!
另:基类和派生类指针兼容与转换问题也测了一下,结果比较符合我“想当然”的判断。。
到底派生类的constructor怎么定义,把基类的成员用using声明了一遍,但是constructor的初始化列表会提示找不到成员n
//派生类使用using声明恢复继承成员的访问级别。
#include<iostream>
class Base{
public:
std::size_t size() const { return n; }
protected:
std::size_t n;
};
class Derived : private Base{//private继承,全部成员变成私有
public:
using Base::size;
//using Base::n;//神奇了,可以提升为public,直接d1.n就访问了。神奇的不是Geany编译器和g++吧
protected:
//using Base::n;
private://声明成private也行啊。。。到底何谓“不能使访问级别比基类中原来指定的更严格或更宽松”
using Base::n;//无论声明放在protected还是private后边,d1.n都提示n是protected。但public...
//~小失误,把基类的n设为private,这种情况到底有何不同~恢复为private也有错啊?
};
class Public_derived : public Base{//private继承,全部成员变成私有
public:
//using Base::size;
protected:
//using Base::n;
private:
//using Base::n;
};
int main(){
/*Base b1;
Derived d1;
Public_derived pd1;
//猜测:一个对象的存储区域是顺序存放各类对象的,首地址是基类子对象,其次是派生类多出来的部分,再次是派生类的派生类。。。
Base *bp1 = &d1;//private继承已经改变了基类的访问权限,所以基类指针也不能指向它了~“Base是Derived里不能访问的一部分”,因此public继承是一个前提。
bp1 = &pd1;
Public_derived *pdp1 = bp1; //前提:public。派生类的指针是不能指向基类的对象的,只能向下兼容
Derived *dp1 = &b1; //不能向上兼容,所以和地址猜想不冲突,这说明很可能就是哪样排列的,所以不能分。
*/
Derived d1;
std::cout << d1.n;//这提升权限到public,但是无法初始化,我始终都搞不定派生类的初始化。。。
}
默认继承保护级别(前边疑问的class和struct有解了):
default inheritance.cpp
比较简单的概念,默认不重要,自己可以手动设置
//默认继承保护级别
class Base{};
struct D1 : Base{}; //public inheritance by default
class D2 : Base{}; //private inheritance by default
//这只是默认的,如果你每次都指定,还是无所谓。。。
//原书:class和struct唯一的不同是默认的成员保护级别和默认的派生保护级别(这俩词指什么)
//以下D3和D4的定义两两相同
class D3 : public Base{
public:
/*...*/
};
//equivalent definition of D3
struct D3 : Base { //inheritance public by default
/*...*/ //initial number access public by default
};
struct D4 : Base {
private:
/*...*/
};
//equivalent definition of D4
class D4 : Base { //inheritance private by default
/*...*/ //initial member access private by default
};
//tips:因为私有继承在使用class保留字是默认情况,但因为实践中使用罕见,所以还要显式的使用private
int main(){
}
为何可以访问,却不可以利用构造函数初始化基类成员,派生类中的基类成员,莫非也用基类的构造函数来完成
class Gif : public Picture_format{
public:
Gif(size_t i = 20) : pixels(i) {}
size_t fcn(){ return pixels; }
};
pe15_11.cpp
弄明白的东西:
继承来的成员的地位:
派生类的constructor无法在初始化列表中初始化继承成员,识别不到
对派生类对象来说,继承的成员也是基类的constructor初始化的,但是派生类能直接读取它,fcn()中使用pixels
如此说来,基类派生类貌似真是分开的模块
class Picture_format{
public:
Picture_format(size_t i = 10) : pixels(i) {}
protected:
size_t pixels;//像素
private:
};
class Gif : public Picture_format{
public:
size_t fcn(){ return pixels; }
};
//Gif g();//这个g不算类Gif的类对象,算个函数什么的吧?!
Gif g;
std::cout << g.fcn() << std::endl;