0

我对在 C++ 中进行强制转换有疑问。我将通过一个例子来解释它。想象一下我有两个课程:

class c1 {
  public:
  c1() {}

  double getHi() { return _hi; }  

private:
  double _hi = 2;
}

class c2 : c1 {
  public:
  c2() {}
} 

由于 c2 是 c1 的子节点,因此它继承了函数 getHi()。因此,您可以使用 c2 的实例调用 getHi。

但是,如果你这样做会发生什么?:

c2* b = new c2();
cout << b->getHi() << endl;
cout << ((c1*)b)->getHi() << endl;

第一个将起作用。但不是第二个。为什么是这样?谁能给我解释一下?

谢谢

编辑:这是一个例子。我写的时候打错了。

4

3 回答 3

2

由于 c2 是 c1 的子节点,因此它继承了函数 getHi()

首先,您应该说c2“派生自”,或“是的派生类”,或“继承(在您的情况下是私下)从” c1。此外,“继承”是正确的动词。

但是,如果你这样做会发生什么?

在这种情况下,无法执行强制转换,因为您从c1. 更改c2如下定义,您将看到两个调用以getHi()完全相同的方式工作(在本例中):

class c2 : public c1 { };
//         ^^^^^^
//         This means that public members of c1 will become
//         public members of c2 as well. If you specify nothing,
//         public members of c1 will become private members of
//         c2 

请注意,您还缺少类定义后的分号,最重要的是,和public定义中的访问修饰符:没有它们,构造函数将是,因此您将根本无法实例化这些类:c1c2private

class c1
{
public: // <== Don't forget this!
  c1() {} // Btw, why this? It does nothing
  double getHi() { return _hi; }
private:
  double _hi = 2;
}; // <== Don't forget this!

class c2 : public c1
//         ^^^^^^ Don'f forget this!
{
public: // <== Don't forget this!
    c2() {} // Btw, why this? It does nothing
}; // <== Don't forget this!

int main()
{
    c2* b = new c2();
    b->getHi();          // Compiles, calls c1::getHi();
    ((c1*)b)->getHi();   // Compiles, calls c1::getHi();
}
于 2013-03-05T15:33:53.727 回答
0

您声明的方式c2使: 外部代码不能因此而成为c1私有基础c1bc1

要修复,请创建c1一个公共基础:

class c2: public c1 {
    ...
};
于 2013-03-05T15:32:24.340 回答
0

在 c++ 代码中使用 c 样式转换的错误形式。请改用 static_cast<> 或 dynamic_cast<> 。除此之外,在您的示例中,您私下继承了 c1 。如果您将其更改为:

class c2 : public c1 {

它可能会更好。

于 2013-03-05T15:34:11.467 回答