下面的代码编译结果报错。
test.c: In function `int main(int, char**)':
test.c:18:22: error: `virtual void TEST2::testxiongyf()' is private
test.c:60:25: error: within this context
但是看60行。
如果把private切换为public,你会发现。
k4->testxiongyf();实际上调用的是TEST类的虚函数,是public的。
也就是编译器对于私有公有的,没有一个整体的扫描。从k4发现是TEST2的。所以就认为是要调用TEST2的虚函数,
所以导致编译导致说出错。
可以认为是编译器的小BUG,或者说编译器就是如此设计,免得繁琐。
那如何会避免出现编译错误呢?强制转换类型看看。
((TEST *)k4)->testxiongyf();
发现,确实可以编译过了!!。而且如果把红色字体部分打开,可以看出可以调用到private的回调,多态性也能体现。
说到底,欺骗编译器或者说规避编译器的坑。
这种测试只是为了学习实验,不是在实际中这样用。
在实践中,也经常看到。如果虚函数被定义为PRIVATE,只要基类的是PUBLIC,也可以而且允许通过基类间接访问到。
#include "stdio.h"
class TEST{
int a;
int b;
public :
virtual void testxiongyf()
{
printf("test111\n");
}
};
class TEST2:public TEST
{
private:
virtual void testxiongyf()
{
printf("test222\n");
}
};
int test(TEST *AA)
{
// AA.testxiongyf();
AA->testxiongyf();
(*AA).testxiongyf();
}
int main(int argc,char *argv[] )
{
TEST k3;
TEST2 k2;
TEST *k1=&k2;
TEST2 *k4;
TEST *k5;
printf("%d\n");
k1->testxiongyf();
k3= *(TEST*)&k2;
k4=(TEST2 *)&k3;
k3.testxiongyf();
(&k3)->testxiongyf();
//*(int *)&k3=*(int*)&k2;
(&k3)->testxiongyf();
k5=&k3;
k5->testxiongyf();
k3.testxiongyf();
printf("k3 %x,k4 %x\n",&k3,k4);
k4->testxiongyf();
// (*k4).testxiongyf();
// test(&k3);
}