首页 > 解决方案 > 如何通过将对象传递给另一个派生类来访问其派生类的基类的受保护数据成员

问题描述

我已经查找了这个问题的一些答案并让它工作,但我似乎无法理解这个答案是如何工作的,有人可以告诉我发生了什么void show(input& obj){cout <<obj.*&output::x <<' ' <<obj.*&output::y <<endl;}。这是完整的代码:

#include <iostream>
using namespace std;
class baseClass{
protected:
    int x, y;
public:
    virtual void func()=0;
};
class input:public baseClass{
public:
    void func(){
        cout <<"Enter value x and y respectively: ";
        cin >>x >>y;
        cout <<endl;
    }
};
class output:public baseClass{
public:
    void func(){}
    void show(input& obj){
        cout <<obj.*&output::x <<' ' <<obj.*&output::y <<endl;    /*Is this a reliable and effective
    }                                                              way of calling the protected data members?*/
};
int main(){
baseClass* ptr;
input callIn;
output callOut;
ptr=&callIn;
ptr->func();
callOut.show(callIn);
}

我正在尝试通过将对象传递给另一个子类来访问从父基类继承的输入类的受保护数据成员。

标签: c++

解决方案


该代码是合法的,尽管复杂且不直观。

魔术的要点发生在这里:

cout <<obj.*&output::x <<' ' <<obj.*&output::y <<endl;

这里,&output::x表示指向成员的指针,即xoutput类中。此操作是允许的,因为outputbaseClass是父级,因此可以访问它的受保护成员。

现在您可以input使用指向成员的指针访问类中的成员,因为访问控制不通过指向成员的指针来控制访问(它们不能!)。它们依赖于在获取所述成员的地址期间调用的控制。

为了使代码更清晰,可以使用局部变量来存储指针:

   int baseClass::* p = &output::y;
   cout << obj.*p << endl; 

此外,虽然我发现这项技术值得理解,但我并不是在讨论它是否适合使用。通常,如果您不得不求助于这样的魔术技巧,您可能想要重新审视您的设计和类层次结构,但我不排除这方面的潜在用例。


推荐阅读