2

I'd like to know if it is best practice to initialize members of an abstract class (has at least one pure virtual member-function, possibly the dtor). The other choice is to do it in the inheriting classes.

Initializing in inheriting class

class IPlayer
{
public:
        virtual ~IPlayer() {};

protected:
        bool m_alive;
};

class Bomber : protected IPlayer
{
public:
        Bomb(bool t_alive = true)
        {
                m_alive = t_alive;
        }
        ~Bomb();
};

Initializing in parent, abstract class

class IPlayer
{
public:
        virtual ~IPlayer() {};

protected:
        bool m_alive { true };
};

class Bomber : protected IPlayer
{
public:
        Bomb();
        ~Bomb();
};

Which one should I prefer, and why?

Community
  • 1
  • 1
SpectreVert
  • 187
  • 2
  • 10
  • Provide a `protected` constructor to `IPlayer` that would perform correct initialization, and eventually hide `m_alive`. – Holt Jun 04 '19 at 09:40
  • In general, there are no crucial differences. If you instantiate it in parent class then think of it as default initialization for classes. As an aside, you shouldn't inherit `IPlayer` in protected mode as then you can't cast to it by standart means. – ALX23z Jun 04 '19 at 10:06

1 Answers1

2

Stricly speaking, if a member is not initialized by in-class-initializer, ctor-init-list, in case of static / thread storage class zero-initialization, or in case of aggregates value-initialization or aggregate-initialization, it will be default-initialized, which leaves types like bool indeterminate.

You can thereafter assign them, but it's not the same thing.

Now we come to the next part:
Every class should enforce its own invariants as far as reasonably possible. Yes, having non-private members reduces that ability, but the convenience, which can translate to fewer copies and thus potentially more efficiency, is sometimes worth it.

Also, you shouldn't repeat yourself needlessly.

So, use the in-class initializer.

Deduplicator
  • 44,692
  • 7
  • 66
  • 118