私人遗产、公共遗产和受保护遗产之间的区别

在C++中,"public"、"private "和 "protected "的继承有什么区别?我在SO上找到的所有问题都是针对特定情况的。

class A 
{
public:
    int x;
protected:
    int y;
private:
    int z;
};

class B : public A
{
    // x is public
    // y is protected
    // z is not accessible from B
};

class C : protected A
{
    // x is protected
    // y is protected
    // z is not accessible from C
};

class D : private A    // 'private' is default for classes
{
    // x is private
    // y is private
    // z is not accessible from D
};

重要提示。 B,C和D类都包含变量x,y和z。 这只是访问的问题。

关于protected和private继承的用法,你可以阅读这里

1:

评论(3)
解决办法

为了回答这个问题,我想先用我自己的话来描述一下会员的访问器。如果你已经知道这些,请跳到标题"下一个:"。

我所知道的访问器有三个。publicprotectedprivate

让。

class Base {
    public:
        int publicMember;
    protected:
        int protectedMember;
    private:
        int privateMember;
};
  • 所有意识到Base'的东西也都意识到Base'包含`publicMember'。
  • 只有子女(和他们的子女)知道Base包含protectedMember
  • 除了Base,没有人知道privateMember

我所说的 "知道 "是指 "承认存在,并能够访问"。

接下来。

同样的情况发生在公有、私有和受保护的继承上。让我们考虑一个 "Base "类和一个继承自 "Base "的 "Child "类。

  • 如果继承是 "公共 "的,所有知道 "Base "和 "Child "的人也都知道 "Child "继承自 "Base"。
  • 如果继承是 "受保护的",只有 "子 "和它的 "子 "知道它们继承自 "基地"。
  • 如果继承是 "私有 "的,除了 "子 "之外,没有人知道继承的情况。
评论(12)

限制继承的可见性将使代码无法看到某个类继承了另一个类。 从派生类到基类的隐式转换不起作用,从基类到派生类的static_cast也不起作用。

只有类的成员/朋友可以看到私有继承,只有成员/朋友和派生类可以看到保护继承。

公共继承

  1. IS-A继承。 一个按钮就是一个窗口,凡是需要窗口的地方,也可以传递一个按钮。

class button : public window { }。

保护的继承

  1. 受保护的执行条款。 很少用。 在boost::compressed_pair中使用,从空类派生,使用空基类优化,节省内存(下面的例子不使用模板一直在点)。

struct empty_pair_impl : 保护 empty_class_1 { non_empty_class_2 second; };

struct pair : 私有的empty_pair_impl { non_empty_class_2 &second() { return this->第二。 }

empty_class_1 &first() { return this; //注意我们返回this! } };

私有继承

  1. 实现的条款。 基类的用法只是为了实现派生类。 对于特质和如果大小很重要的话,很有用(只包含函数的空特质会利用空基类优化)。 不过往往包含是更好的解决方案。 对于字符串来说,大小是至关重要的,所以这里经常看到的用法是'。

template 字符串结构。 私有存储模型 { public.void realloc() { void realloc() { // 使用继承的功能 StorageModel::realloc()。 } };


公共成员

  1. 总数

类对 { 公开。 第一名: 第二个第二。 };

2.附件

窗口类 { public.int getWidth()const; int int getWidth() const; };

受保护的成员

  1. 为派生类提供更多的访问机会

类栈 { 保护。 vector c; };

类窗口 { 保护的。 void registerClass(window_descriptor w); };

private成员

  1. 保持实施细节

窗口类 { 私有的。 int width; };


请注意,C-style casts特意允许以定义的、安全的方式将派生类投向受保护的或私有的基类,也可以投向另一个方向。 应该不惜一切代价避免这样做,因为它会使代码依赖于实现细节--但如果有必要,你可以利用这种技术。

评论(1)

这与基类的公共成员如何从派生类中暴露出来有关。

  • public ->基类的公共成员将是公共的(通常是默认的)。
  • protected ->基类的公共成员将被保护。
  • private -> 基类的公共成员将是私有的。

正如Litb所指出的,公共继承是传统的继承,你会在大多数编程语言中看到。也就是说,它模拟了一种"IS-A"关系。私有继承,AFAIK是C++特有的东西,是一种"实施于"的关系。也就是说,你想在派生类中**使用公共接口,但不希望派生类的用户能够访问该接口。许多人认为,在这种情况下,你应该聚合基类,也就是说,不要把基类作为一个私有的基类,而是把它作为派生类的一个成员,以便重新使用基类的功能。

评论(2)

这三个关键字也在完全不同的上下文中用于指定可见性继承模型

这个表收集了所有可能的组件声明和继承模型的组合,呈现了子类完全定义后对组件的访问结果。

![在此输入图像描述][1] 。

上表的解释如下(看看第一行)。

*如果一个组件被声明公共,并且它的类被继承公共,那么由此产生的访问就是公共

举个例子。

 class Super {
    public:      int p;
    private:     int q;
    protected:   int r;
 };

 class Sub : private Super {};

 class Subsub : public Sub {};

在类Sub中,变量pqr的访问结果是none

另一个例子。

class Super {
    private:     int x;
    protected:   int y;
    public:      int z;
 };
class Sub : protected Super {};

结果,在类Sub中,变量yz的访问是保护,变量x的访问是

一个更详细的例子。


class Super {
private:
    int storage;
public:
    void put(int val) { storage = val;  }
    int  get(void)    { return storage; }
};
int main(void) {
    Super object;

    object.put(100);
    object.put(object.get());
    cout 
评论(2)
Member in base class : Private   Protected   Public   

继承类型

Private            :   Inaccessible   Private     Private   
Protected          :   Inaccessible   Protected   Protected  
Public             :   Inaccessible   Protected   Public
评论(1)

1)公共继承

a. Base类的私有成员在Derived类中不可访问。

b. Base类的受保护成员在派生类中仍然受保护。

c. Base类的公共成员在派生类中仍然是公共的,所以其他类可以通过派生类对象使用Base类的公共成员。

c. Base类的公共成员在Derived类中仍然是公共的,因此,其他类可以通过Derived类对象使用Base类的公共成员。

2)受保护的继承

a. Base类的私有成员在Derived类中是不可访问的。

b. Base类的受保护成员在Derived类中仍然受保护。

c. Base类的公共成员也会成为Derived类的保护成员。

所以,其他类不能通过派生类对象使用Base类的公共成员。 但它们可以被衍生类的子类使用。

3) Private Inheritance

a. Base类的私有成员在Derived类中是不可访问的。

b. 受保护的&amp.public成员在派生类中成为私有成员。 b. Base类的public成员变成了Derived类的private成员,所以Base类的成员不能通过Derived类被其他类访问。

所以,Base类的成员不能被其他类通过Derived类对象访问,因为它们在Derived类中是私有成员。 所以,即使是Derived类的子类,也不能通过Derived类对象访问Base类的成员。 类不能访问它们。

评论(0)

公共继承模型是一种IS-A关系。 有了

class B {};
class D : public B {};

每一个D都是一个B

Private inheritance model an IS-IMPLEMENTED-USING relationship (or whatever that's called). 有了

class B {};
class D : private B {};

D'不是B',但每一个D'在其实现中都使用它的B'。 私有继承总是可以通过使用 containment 来消除。

class B {};
class D {
  private: 
    B b_;
};

这个 "D",也可以用 "B "来实现,在这里用它的 "b_"来实现。 与继承相比,containment在类型之间的耦合性不那么紧密,所以一般情况下应该首选containment。 有时使用containment代替私有继承,不如私有继承方便。 往往这是一个蹩脚的借口,因为懒惰。

我想没有人知道什么是 "保护 "继承模型。 至少我还没有看到任何有说服力的解释。

评论(4)

如果你从另一个类中公开继承,每个人都知道你在继承,并且你可以通过基类指针被任何人多态地使用。

如果你以保护方式继承,只有你的子类能够多态地使用你。

如果你是私有继承,只有你自己能够执行父类的方法。

这基本上象征着其余的类对你和你的父类关系的了解

评论(0)

受保护的数据成员可以被任何继承自你的类的类访问。 但是,私有数据成员却不能。 假设我们有以下内容。

class MyClass {
    private:
        int myPrivateMember;    // lol
    protected:
        int myProtectedMember;
};

在你对这个类的扩展中,引用this.myPrivateMember是行不通的,但是this.myProtectedMember可以。 但是,this.myProtectedMember可以。 该值仍然是封装的,所以如果我们有一个名为myObj的这个类的实例化,那么myObj.myProtectedMember就不会工作,所以它的功能类似于私有数据成员。

评论(0)
Accessors    | Base Class | Derived Class | World
—————————————+————————————+———————————————+———————
public       |      y     |       y       |   y
—————————————+————————————+———————————————+———————
protected    |      y     |       y       |   n
—————————————+————————————+———————————————+———————
private      |            |               |    
  or         |      y     |       n       |   n
no accessor  |            |               |

y: accessible
n: not accessible

基于这个java的例子...... 我觉得一个小表格胜过千言万语:)

评论(3)

小结。

  • 私人的。 除了班级内部的人,没有人可以看到它。
  • 受保护的。 私有+派生类可以看到它
  • 公开。 全世界都能看到

当继承时,你可以(在某些语言中)朝一定的方向改变数据成员的保护类型,例如:从protected到public。 从 protected 到 public。

评论(0)

私人的。

一个基类的私有成员只能被该基类的成员访问。

公共的。 一个基类的公共成员可以被该基类的成员、派生类的成员以及基类和派生类之外的成员访问。

受保护的。

基类的保护成员可以被基类的成员和派生类的成员访问。


简而言之..:

私人:基础

受保护的。 基数+派生

公共。 基础+派生+任何其他成员

评论(0)

我找到了一个简单的答案,所以也想把它贴出来供我将来参考。

其来自链接http://www.learncpp.com/cpp-tutorial/115-inheritance-and-access-specifiers/

class Base
{
public:
    int m_nPublic; // can be accessed by anybody
private:
    int m_nPrivate; // can only be accessed by Base member functions (but not derived classes)
protected:
    int m_nProtected; // can be accessed by Base member functions, or derived classes.
};

class Derived: public Base
{
public:
    Derived()
    {
        // Derived's access to Base members is not influenced by the type of inheritance used,
        // so the following is always true:

        m_nPublic = 1; // allowed: can access public base members from derived class
        m_nPrivate = 2; // not allowed: can not access private base members from derived class
        m_nProtected = 3; // allowed: can access protected base members from derived class
    }
};

int main()
{
    Base cBase;
    cBase.m_nPublic = 1; // allowed: can access public members from outside class
    cBase.m_nPrivate = 2; // not allowed: can not access private members from outside class
    cBase.m_nProtected = 3; // not allowed: can not access protected members from outside class
}
评论(0)

它本质上是对派生类中基类的公共和受保护成员的访问保护。 通过公有继承,派生类可以看到基类的公有和受保护成员。 如果是私有继承,它就不能。 通过保护,派生类和任何派生类都可以看到它们。

评论(0)