【问题标题】:Access private data type in base class if only private function exist如果仅存在私有函数,则访问基类中的私有数据类型
【发布时间】:2015-04-12 11:56:03
【问题描述】:

鉴于下面的代码,如果基类中的函数通过继承保护,我们可以访问基类的私有数据。我的问题是,如果基类中的所有方法也都设置为私有,我们有什么方法可以访问私有数据?

class Base

{
int i;

protected:
  void set(int data){
      i = data;
  }
  int get(){
      return i;
  }
};

class derive: Base{
public:
    void change(int x){
        set(x);
        cout<<get()<<endl;
    }
};

int main()
{
   derive b;
   b.change(3);
   return 0;    
}

【问题讨论】:

  • 呃,不,因为没有其他人可以打电话给他们。

标签: c++ inheritance private


【解决方案1】:

“如果基类中的函数通过继承保护,我们可以访问基类的私有数据”,不,你并没有真正访问私有数据。您正在为您执行此操作的基类中调用 setter。不,您将无法调用基类的私有方法。

【讨论】:

  • 感谢指正。那么如果数据和函数都是私有的,那么就没有办法访问私有数据吗?我在一次采访中被问到这个问题,我说没办法。但从面试官的回答来看,我想还是有一些比较棘手的方法来实现的。
  • 如果这是一个“技巧问题”,虽然有办法通过在基类定义中添加 friend class derive; 来做到这一点,但这纯粹是邪恶的。
  • 面试官不应该问“诡计问题”。但如果他不喜欢你的回答,你应该问他,并评估一下。他可能是错的。
  • 我从没想过使用朋友类派生。谢谢!
【解决方案2】:

在基类中将成员设置为私有将使其对所有子类也都是私有的。您可以定义新的公共函数来更改子项中的这些成员。

【讨论】:

    【解决方案3】:

    通过使用friend 使派生类成为 Base 的朋友

    class derive;//forward declaration
    class Base
    {
    int i;
    
    private:
      void set(int data){
          i = data;
      }
    protected:
      int get(){
          return i;
      }
    public:
      friend class derive;
    };
    
    class derive : public Base{
    public:
        void change(int x){
            set(x);
            cout<<get()<<endl;
        }
    };
    

    您应该注意公共/受保护的继承。 class a : public/protected b

    不要使用访问说明符重载/覆盖:

    现在我展示如何重新声明继承成员的访问说明符:

    class derive : public Base{
    public:
        Base::set;//this is valid redeclaration within public scope. Now anybody could use derive::set(x)
        void change(int x){
            set(x);
            cout<<get()<<endl;
        }
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2023-03-04
      • 2016-07-25
      • 2011-12-29
      • 2011-02-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-01-20
      相关资源
      最近更新 更多