Reputation: 1519
Apologize for the verbose title. I do not know how to express this succinctly.
class A
{
bool a1;
unsigned int a2 ;
virtual bool aFn1(unsigned int t_) = 0 ;
virtual void aFn2(unsigned int t_, bool val_) = 0 ;
A()
{
a1 = false ; a2 = 0 ;
};
}
Next:
#include <bitset>
#define MAX_SIZE 500
class B : public class A
{
private:
std::bitset<MAX_SIZE> _bmem;
public:
B() : A() {};
using A::aFn1 ;
virtual bool aFn1(unsigned int t_)
{
return _bemem[t_]
}
using A::aFn2;
virtual void aFn2(unsigned int t_, bool val_)
{
_bemem[t_] = val_ ;
}
}
Next:
#include "A.h"
#include "B.h"
std::vector<A*> * vecA;
vecA = new std::vector<B*> ;
But this last step does not work. clang complete tells me
assigning to
std::vector<A*> *
from incompatible typestd::vector<B*>
But since B
derives from A
, this should be possible right? I have seen examples where people use
B bObj;
A *aObj = &bObj ;
So could you please tell me what mistake I am making?
The reason I go through all this, is because I have class C
and class D
, exactly like class B
, where the only difference is that #define MAX_SIZE
is different.
I do this because, I need a bitset
of different sizes, to be used in different phases of the program. And bitset
requires the number of elements it needs to store at compile time.
Upvotes: 0
Views: 413
Reputation: 30831
This boils down to
std::vector<Base*> *v = new std::vector<Derived*>;
But std::vector<Base*>
and std::vector<Derived*>
aren't compatible types, for the same reason that you can't use an array of Derived*
as an array of Base*
.
For example, in the above, what should happen if you write v->push_back(new Base())
? You can't have a Base*
in your vector of Derived*
.
For a good explanation of the issues involved in treating a Derived*
as a Base*
, see also the reasoning behind this answer to "Converting std::function<void(Derived*)>
to std::function<void(Base*)>
", which is the same issue in a different guise.
Upvotes: 0
Reputation: 275395
You are using far too many interfaces and pointers.
class A {
bool a1 = false;
unsigned int a2 = 0;
std::vector<bool> values;
bool aFn1(unsigned int t_) const { return values[t_]; }
void aFn2(unsigned int t_, bool val_) { values[t_] = val_; }
void set_size(size_t i){values.resize(i);}
A() = default;
static A of_size(size_t i){ A r; r.set_size(i); return r; }
};
then use a std::vector<A>
.
If you 100 elements of size 500, do std::vector<A> v( 100, A::of_size(500) );
This code will do fewer allocations, use less memory, and have less indirection than your code. Using new
is "code smell", often a sign you have made a mistake, unless you really need objects of extremely complex lifespan.
A std::vector<bool> values
will be nearly as compact as a std::bitset<500>
, and the difference is made up by the other pointers I eliminated.
Upvotes: 3
Reputation: 238351
clang complete tells me
assigning to std::vector<A*> * from incompatible type
...
Clang tells you the truth.
But since B derives from A, this should be possible right?
Not right.
I have seen examples where people use
B bObj;
A *aObj = &bObj ;
Those examples are correct. They work because A
is a parent of B
. A pointer of a child class can be converted to a pointer to a parent class.
So could you please tell me what mistake I am making?
You're trying to assign a pointer to std::vector<B*>
into a pointer to std::vector<A*>
. std::vector<A*>
is not a parent of std::vector<B*>
. In terms of inheritance they are entirely unrelated classes. Pointer to a type cannot be converted to a pointer to an unrelated type.
Upvotes: 2
Reputation: 65620
You cannot make a std::vector<A*>*
point to a std::vector<B*>*
, those are disparate types.
What you can do is push B*
into a std::vector<A*>
:
std::vector<A*> vec;
B b;
vec.push_back(&b);
Of course you need to be careful about the lifetime of the pointers. You might want to use std::unique_ptr
if the vector should manage the lifetime itself.
Also note that A
needs a virtual destructor, otherwise it is undefined behaviour to delete a B*
through an A*
.
Upvotes: 2