-1

Let's say I have a base class and two derived classes:

class a {};
class b : a { int a; };
class c : a { int b; };

And I have a list of the base class, and I insert the derived class into the list:

std::list<a> list;

list.emplace_back(b());
list.emplace_back(c());

Now, I want to access int a like this:

for(auto i : list)
{
    i.a = 5;
}

I already have checks in place to see what class it is, but the compiler is still not letting me access it.

How can I access any field in the derived class from the base class?

This question has been asked many times, but none of the methods have worked for me so far.

Remy Lebeau
  • 555,201
  • 31
  • 458
  • 770
MaxCE
  • 7
  • 3

1 Answers1

1

First, you need a list of base class pointers, otherwise you will slice the objects when you insert them into the list.

Then, you need to type-cast the pointers to access derived classes as needed.

If all of the list elements are pointing at the same derived type, you can use static_cast:

struct A {};
struct B : A { int a; };
struct C : A { int b; };

std::list<std::unique_ptr<A>> lst;

lst.push_back(std::make_unique<B>());
lst.push_back(std::make_unique<B>());

for(auto &ptr : lst)
{
    static_cast<B*>(ptr.get())->a = 5;
}

Otherwise, use dynamic_cast instead to test the derived class type before accessing its fields:

struct A {};
struct B : A { int a; };
struct C : A { int b; };

std::list<std::unique_ptr<A>> lst;

lst.push_back(std::make_unique<B>());
lst.push_back(std::make_unique<C>());

for(auto &ptr : lst)
{
    B *b = dynamic_cast<B*>(ptr.get());
    if (b)
        b->a = 5;
}
Remy Lebeau
  • 555,201
  • 31
  • 458
  • 770
  • Disclaimer: the author if this post will not held responsible for damages caused by paying the cost of runtime polymorphism without any apparent advantage – MatG Oct 09 '21 at 06:36
  • really appreciate this, i'm surprised that of all the people that have asked this question no one has given this answer – MaxCE Oct 09 '21 at 12:53
  • @MatG Granted, polymorphism should be used to abstract away details like this, but there are also valid use-cases for wanting to access specific fields, too. We are here to share knowledge and answer questions on how to do specific things. And sure, suggest better choices, too. – Remy Lebeau Oct 09 '21 at 15:43
  • @MaxCE there are plenty of questions on SO that have answers demonstrating the use of polymorphism with typecasting pointers to access derived classes. It is just that when using polymorphism the way it is intended, you shouldn't *need* to do that in the first place. – Remy Lebeau Oct 09 '21 at 15:45
  • @RemyLebeau That was a little joke, you strictly answered the question – MatG Oct 09 '21 at 17:12
  • @MaxCE To show your appreciation you should also upvote the answer, I'll do that for you – MatG Oct 09 '21 at 17:14
  • @matG i can't i need to have 15 reputation – MaxCE Oct 09 '21 at 21:56
  • @MaxCE That's the reason I did that for you – MatG Oct 10 '21 at 06:27