user1770094
user1770094

Reputation: 87

Virtual functions error?

So I made this class:

    class Book
    {
        public:
            Book(string newTitle = "???", string newAuthor = "???");
            virtual ~Book();

            string getTitle();
            string getAuthor();
            void setTitle(string  newTitle);
            void setAuthor(string newAuthor);

            virtual string allInfo();

        private:
            string title;
            string author;
    };

And I was going to cover the allInfo()-function in two other classes One called HardcoverBooks and another called AudioBooks. Both inheriting from Book.

This is what I did subsequently in the .cpp files in both classes, first the AudioBook class:

string AudioBook::allInfo(){
    stringstream newString;

    newString<<"Title: "<<this->title<<endl<<"Author: "<<this->author<<endl
             <<"Narrator: "<<this->narrator<<endl
             <<"Length(in minutes):     "<<this->length<<endl<<endl;

    return newString.str();
}

And this in the HardcoverBook class:

string HardcoverBook::allInfo(){
    stringstream newString;

    newString<<"Title: "<<this->title<<endl<<"Author: "<<this->author<<endl
             <<"Pages: "<<this->pages<<endl<<endl;

    return newString.str();
}

Everything is working fine and dandy,except that the AudioBook class is complaining about this:

include\Book.h||In member function 'virtual std::string AudioBook::allInfo()':| include\Book.h|41|error: 'std::string Book::title' is private| mningsuppgiftIIB\src\AudioBook.cpp|27|error: within this context| include\Book.h|42|error: 'std::string Book::author' is private| mningsuppgiftIIB\src\AudioBook.cpp|27|error: within this context| ||=== Build finished: 4 errors, 0 warnings ===|

But in HardcoverBook it doesn't complain about this at all,strangely enough.

My questions:

  1. What do I do to make this work? (i.e. to make both classes be able to use the function allInfo() in their own way)

  2. Why doesn't it work like this?

EDIT: This is some homework I'm doing,and one of the requirements is to make the member variables and properties private. So protected does work,kudos for that guys,but I'll add another bonus question:

  1. How do I make it work with private member variables?

Upvotes: 0

Views: 103

Answers (3)

David Heffernan
David Heffernan

Reputation: 612794

The title and author members are private. Which means that they are not visible in sub-classes, like AudioBook.

In order to make them visible to sub-classes you need to make these members protected rather than private.

Another option is to leave the member fields as private, and add protected or public access methods to allow the values to be read. For example:

public:
    string getAuthor()
    {
        return author;
    }

I would also comment that I don't understand why you are using this-> to access members of your class. There's no need for that and it's usually best to simply omit it.


Without seeing your homework assignment, I'm not 100% sure what to make of the requirement that

member variables and properties are private

My guess is that your task is to override allInfo(). You are being asked to extend the string returned to include all the information included by the base class implementation, and add some more.

Your current attempt simply duplicates the code in Book::allInfo(). And that's the problem. In order for that to work, the derived classes need access to the private members. And you are not allowed to do that. So, your solution will have to involve calling allInfo() on the base class, and then appending to the string that the base class implementation returns.

Since this is homework, I will refrain from implementing this for you!

Upvotes: 3

masoud
masoud

Reputation: 56479

Make your members protected to access them via derived classes:

  protected:
            string title;
            string author;

Otherwise, they are invisible for derived classes.

Private and Protected Members:

Public members of a class A are accessible for all and everyone.

Protected members of a class A are not accessible outside of A's code, but is accessible from the code of any class derived from A.

Private members of a class A are not accessible outside of A's code, or from the code of any class derived from A.

If you want leave them private, the other way is to create protected or public access methods for them.

Upvotes: 2

meyumer
meyumer

Reputation: 5064

You should convert the private members to:

protected:
    string title;
    string author;

This way the sub-classes can access them.

Upvotes: 1

Related Questions