Base and derived classes and more

closed account (G1vDizwU)
I can't understand these sentences completely. Could anyone explain thses to me please?


A base can be private, protected, or public.

- If a base of class D is private, its public and protected member names can be used only by members of D.

- If a base of class D is protected, its public and protected member names can be used only by members of D and members of classes derived from D.

- If a base is public, its public member names can be used by all functions.
Last edited on
I think it is poorly written, because it is not being careful to distinguish between a class and a member function.

Unless you know what you are doing, classes should always use public inheritance.

The member functions are visible to other classes depending on their status as private, protected, and public.

- A public member function can be used by anything that has access to your class.

- A protected member function can only be used by classes derived from your class. (And the class itself, of course.)

- A private member function can only be used by the class itself.


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
#include <iostream>

struct A
{
  public:
    void one() const { std::cout << "1\n"; }
  protected:
    void two() const { std::cout << "2\n"; }
  private:
    void three() const { std::cout << "3\n"; }

  public:
    A()
    { 
      std::cout << "(ctor A)\n";
      // A class can use all its member functions:
      one(); two(); three();  
    }
};

struct B: public A
{
  B() 
  { 
    std::cout << "(ctor B)\n";
    // A derived class can only use public and protected inherited member functions:
    one(); two();
  }
};

int main()
{
  B b;
  std::cout << "(main)\n";
  b.one();  // Everything else can only use public member functions.
}

Hope this helps.
This is talking about the inheritance of members and methods of classes between base and derived classes.

Whenever you inherit a base class into a derived class the code will look like this:

1
2
3
4
class Derived : public Base // This public specifier is what you're sentences refer to
{
    // Class definition code
};


That public specifier can be swapped for protected or private.

- If a base of class D is private, its public and protected member names can be used only by members of D.
If the specifier of the inherited Base class is inherited as private, that means that all of the members and methods that are inherited by Derived can only be used by Derived. Nothing from the outside can access those members. See below code for example:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
class Foo
{
public:
    void myFooMethod()
    {
        cout << "Inherited from Foo" << endl;
    }
};

class Bar : private Foo
{
public:
    void myBarMethod()
    {
        // This method can be ran from inside of Bar, because
        // it was inherited from Foo.
        myFooMethod();
    }
};

int main()
{
    Bar my_object;

    // This will return as an error because Foo was inherited as private and
    // so it's members cannot be accessed from outside of Bar.
    my_object.myFooMethod();

    // This, however, can be run just as you would expect.
    my_object.myBarMethod();
}


- If a base of class D is protected, its public and protected member names can be used only by members of D and members of classes derived from D.
If the inheritance specifier is protected whenever you inherit from the base class, Foo, the same rules as above apply except that any derived class of the derived class, Bar, can also use the methods and members of the original base class, Foo. See below code for example.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
class Foo
{
public:
    void myFooMethod()
    {
        cout << "Inherited from Foo" << endl;
    }
};

class Bar : protected Foo
{
public:
    void myBarMethod()
    {
        // This method can be ran from inside of Bar, because
        // it was inherited from Foo.
        myFooMethod();
    }
};

class Baz : protected Bar
{
public:
    void myBazMethod()
    {
        // This can be run without error. Notice how this method is inherited from
        // two base classes before. Foo > Bar > Baz
        myFooMethod();
    }
};

int main()
{
    Baz my_object;

    // This will still return an error, because myFooMethod() is still not made public to any
    // use from outside of the derived classes.
    my_object.myFooMethod();

    // This, however, can be run just as you would expect.
    my_object.myBazMethod();
}


- If a base is public, its public member names can be used by all functions.
If the inheritance specifier is declared as public, all of the members being inherited can be accessed from inside or outside of the function. See example below.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
class Foo
{
public:
    void myFooMethod()
    {
        cout << "Inherited from Foo" << endl;
    }
};

class Bar : private Foo
{
public:
    void myBarMethod()
    {
        // This method can be ran from inside of Bar, because
        // it was inherited from Foo.
        myFooMethod();
    }
};

int main()
{
    Bar my_object;

    // This would have returned an error in the past, but this is now a valid
    // code to execute. Foo's methods can be accessed from the public scope.
    my_object.myFooMethod();

    // This can also be run just as you would expect.
    my_object.myBarMethod();
}


-----------------------------

The best way to think about this is by use the names themselves.

- If a class is inherited as private, all of it's public and protected members can only be accessed by the derived class.
- If a class is inherited as protected, all of it's public and protected members can only be accessed by the derived class and any subsequent derived classes of the derived class.
- If a class is inherited as public, all of it's public members (not protected) can be accessed by essentially every other class and function.

Hope this helps,
Tresky
Re: private and protected inheritance, there's a little more to it than that. Marshall Cline has a pretty good writeup here (which I find more readable than the SO link given by coder777 -- still worth reading, though):
https://isocpp.org/wiki/faq/private-inheritance

Again, unless you know what you are doing, avoid them and stick with public inheritance (of classes).

Use public, protected, and private member functions to maintain encapsulation.

Hope this helps.
closed account (G1vDizwU)
Thank you all very much.
Topic archived. No new replies allowed.