请澄清const限定符传播

时间:2016-05-18 09:35:13

标签: c++

假设我们有以下代码:

class Base {
  public:
    int a = 5;
};

class Derived : public Base {
  public:
    Base *parent_ = new Base;
    Base* parent() const { return parent_; }
};

void f(const Derived *derived) {
    Base *p = derived->parent();
    p->a = 10; // <- is this correct?
}

我个人认为这是一个问题:

  

在函数f中,我们使用指向constDerived对象的指针。这使得每个成员const因此parent_变为const Base *。如果它是const,我们就不应该有能力修改指针指向的对象。

我哪里错了?

4 个答案:

答案 0 :(得分:7)

  

这使得它的每个成员也因此parent_成为const Base *

不,指针将成为const本身,而不是它指向的对象。因此parent_变为Base * const,而不是const Base *,并且您的代码有效。

答案 1 :(得分:5)

Base* parent() const { return parent_; }

不幸的是,这是C ++的问题。方法是const,但它返回一个非常量指针,这将允许以下操作成功:

p->a = 10; // <- is this correct?

程序员有责任不从函数返回非常量指针或引用(方法是const或不是const)。

答案 2 :(得分:0)

正如 tobi303 指出的那样,这个答案错误。为了下面的讨论,请将它保存在这里。

我可能错了,但这一行:



没有提到有关返回const对象的任何内容。它相当于

其中 Base* parent() const { return parent_; } Base* parent() const { return this->parent_; } ,但this仍为const Derived*

答案 3 :(得分:0)

const方法仅阻止该方法修改该类的任何非可变数据成员。

如果您不想修改a并且不想更新课程,则需要写一下:

const Base *p = derived->parent();

但是,我建议您不要将类中的非const数据成员作为ref或指针返回,因为这会破坏C ++的数据封装概念。当然,这与公众a相同。