[英]C++ inheritance & virtual function problem
我想显示结果是 2。(现在结果是 1。)
我应该怎么做? (我想调用 B::test()。但实际上代码无法访问 main.c 中的 bh、b.c)
我也想知道从“public: virtual int test() {return 1;}”到“protected: virtual int test() {return 1;}”的错误啊
the inheritance relationship are super class A sub class B super class A sub class C
但我可以在 main.c 中访问 A class 我想要结果 2。(“a.test()”无法调用“b.test()”)
// a.h
#ifndef _A_
#define _A_
class A {
public:
A() {};
~A() {};
//protected:
virtual int test() {return 1;}
private:
friend class B;
};
#endif
// b.h
#ifndef _B_
#define _B_
#include "a.h"
class B : public A {
public:
B() {};
~B() {};
private:
int test() override;
friend class A;
};
#endif
// b.c
#include "b.h"
int B::test()
{
return 2;
}
// c.h
#ifndef _C_
#define _C_
#include "a.h"
class C : public A {
public:
C() {};
~C() {};
private:
int test() override;
friend class A;
};
#endif
// c.c
#include "c.h"
int C::test()
{
return 3;
}
// main.c
#include <iostream>
#include "a.h"
using namespace std;
int main(void)
{
A *a = new A();
cout << a->test() << "\n";
return 0;
}
考虑您的代码:
// main.c
#include <iostream>
#include "a.h"
using namespace std;
int main(void)
{
A *a = new A();
cout << a->test() << "\n";
return 0;
}
行为的关键决定因素是=new A()
。
如果你把它改成=new B()
那么你会得到你想要的 '2' 的结果。
但是,您已经添加了限制“代码无法访问 b.h”。 这意味着=new B()
不会编译。 这个限制从何而来? 您可以使用极其复杂的工厂模式来实现这一点,但这似乎不太可能是您想要做的。
访问说明符( private
, protect
, public
)对于层次结构中的每个级别的相同方法(在本例中为test()
)应该是相同的。 这不是由编译器绝对强制执行的,而是一个明确的最佳实践。 将test()
private
或protected
之间几乎没有什么区别,但在这两种情况下,表达式:
a->test()
将在 main 中失败,因为它在 class 之外,并且只能访问public
成员。
还值得指出的是,您的friend
声明在代码中完全没有必要,如图所示。
创建B
类型的 object ,您仍然可以调用test
方法,因为A::test
是公共的。 此代码将打印 2:
int main(void)
{
A *a = new B();
// ^
cout << a->test() << "\n";
delete a; // (1)
return 0;
}
除非您将A
的析构函数设为虚拟( 何时使用虚拟析构函数? ),否则第 (1) 行也无法正常工作:
class A {
public:
A() {};
virtual ~A() {};
// ^^^^^^^
//protected:
virtual int test() {return 1;}
private:
friend class B;
};
UPD如果由于某种原因您不能包含bh
,您可以执行以下操作:
ah
:
#ifndef _A_
#define _A_
class A {
...
};
A* CreateB();
#endif
a.c
:
#include "a.h"
#include "b.h"
...
A* CreateB() {
return new B();
}
main.c
:
#include <iostream>
#include "a.h"
using namespace std;
int main(void)
{
A *a = CreateB();
cout << a->test() << "\n";
delete a;
return 0;
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.