注册 登录
编程论坛 C++教室

C++为什么在派生类中修改了基类protected数据成员,但基类的protected数据却没有改变

cheetah 发布于 2023-04-21 13:34, 241 次点击
程序代码:
#include <iostream>
#include <cstring>
using std::cout;
using std::endl;
class A
{
protected:
    int n;
public:
    A() {n = 10;}
    void show()
    {
        cout << n << endl;
    }
};
class B : public A
{
public:
    void showb()
    {
        cout << n << endl;
    }
};
class C : public A
{
public:
    void setn()
    {
        n = 100;
    }
};
int main()
{
    A a;
    B b;
    C c;
    b.showb();//显示基类A中的n没毛病
    c.setn();//通过类C重新设置A中的n为100
    b.show();//按理说这里应该是100
    a.show();//这里也应该是100
   
//但实际上其它从A类派生来的全都没有改变,只改变了C中的n
   
//难道派生类不共享基类保护型成员数据吗
    return 0;
}
4 回复
#2
rjsp2023-04-21 14:35
a, b, c 之间又没有任何关系

我简单的问个问题
struct A
{
    int n;
};
int main( void )
{
    A a1{1}; // 此时 a1.n 等于 1,这没有疑问
    A a2{2}; // 此时 a2.n 等于 2,这没有疑问。但你认为 a1.n 也会变为 2 吗?
}


程序代码:
#include <cassert>

struct A
{
    int n;
};
struct B : A
{
};

int main( void )
{
    A a1{1}, a2{2};
    B b{3};

    assert( b.n == 3 );
    assert( a1.n == 1 );
    assert( a2.n == 2 );   
}
#3
cheetah2023-04-21 15:44
回复 2楼 rjsp
谢谢大佬,好像明白了!这么简单的问题居然都没有发现,哎,大佬真是个明白人

[此贴子已经被作者于2023-4-21 15:57编辑过]

#4
东海ECS2023-04-22 11:03
在C++中,派生类可以访问基类中的protected成员,但是这并不意味着修改派生类中的该成员会对基类中的同一成员产生影响。

在这个示例程序中,类B和类C都是派生自类A的。类B中定义了一个公有方法showb(),该方法访问了基类A中的保护型成员n。类C中定义了一个公有方法setn(),该方法修改了基类A中的保护型成员n的值。

但是,需要注意的是,虽然类C的成员函数修改了基类A中的保护型成员的值,但是类B中的成员函数并没有访问类C中修改的那个成员,而是访问的类B自己继承得到的那个成员。这是因为,派生类是独立的类,其实例对象只包含自身的成员,而不包含直接或间接继承得到的基类成员。

因此,在类B中修改基类A中的保护型成员的值并不会对类C中修改后的值产生影响,这两个值相互独立。如果想要在类B中访问类C中修改的那个成员,需要使用指针或引用等方法在两个类之间进行数据共享。
#5
cheetah2023-04-22 12:05
回复 4楼 东海ECS
感谢大佬,说的真好,我认真的看了好几遍,特别是最后那一句话受益非浅!
1