Home > Software engineering >  Polymorphic Smart Pointer Array as Argument
Polymorphic Smart Pointer Array as Argument

Time:10-06

I want a static 2D array that takes an interface class pointer.

Using raw pointer Base* rawr[5][5] works fine but I want to work with smart pointers and only pass the raw pointer as an argument.

How can I make the code work without changing the args to smart pointers?

class Base {};

class Child : public Base {};

void Foo(Base* array[5][5])
{
    // Stuff
}
void OtherFoo(std::unique_ptr<Base> array[5][5])
{
    // Stuff
}

int main()
{
    std::unique_ptr<Base> rawr[5][5];
    
    // argument of type "std::unique_ptr<Base, std::default_delete<Base>> (*)[5]" 
    // is incompatible with parameter of type "Base *(*)[5]"
    Foo(rawr);

    // no suitable conversion function from 
    // "std::unique_ptr<Base, std::default_delete<Base>>" to "Base *(*)[5]" exists
    Foo(rawr[5][5]);
    
    // expression must have class type but it has type 
    // "std::unique_ptr<Base, std::default_delete<Base>> (*)[5]"
    Foo(rawr.get());

    // expression must have pointer-to-class type but it has type 
    // "std::unique_ptr<Base, std::default_delete<Base>> (*)[5]"
    Foo(rawr->get());


    // This works 
    OtherFoo(rawr);
}

Newbie question probably a duplicate but after googling for a while I didn't see an answer, sorry :'(

CodePudding user response:

How can I make the code work without changing the args to smart pointers?

You can't pass around an array of smart pointers where an array of raw pointers is expected. However, you can have 2 separate arrays - an array of smart pointers, and an array of raw pointers that point to the objects that the smart pointers are managing, eg:

class Base {
public:
    virtual ~Base() = default; 
};

class Child : public Base {};

void Foo(Base* array[5][5])
{
    // Stuff
}

void OtherFoo(std::unique_ptr<Base> array[5][5])
{
    // Stuff
}

int main()
{
    std::unique_ptr<Base> smartr[5][5];
    Base* rawr[5][5];
    
    // fill smartr as needed...

    for (int i = 0; i < 5;   i) {
        for(int j = 0; j < 5;   j) {
            rawr[i][j] = smartr[i][j].get();
        }
    }

    Foo(rawr);
    OtherFoo(smartr);
}
  • Related