What pointer type to use, when I do not know the context the pointer are used

96 Views Asked by At

I am developing a library, so I do not know the context of the application, that will later use the library. I have two classes. The Window class registers Widgets, so it can eg. forward ui events to the widgets. The Widget class represents the widget that is shown in the gui.

In scenario#1 the application, that uses the library, creates a widget object, sets the title once and adds it afterwards to the window. In this case I would propose a unique pointer instead of the raw pointer in the AddWidget method. Because the application does not need the widget object anymore. The ownership could be transferred to the window object.

In scenario#2 the application again creates a widget object and adds it to the window. But during runtime the application still needs access to the widget object, to change the title. In this case I would propose a shared pointer instead of the raw pointer in the AddWidget method. Becuase we need a shared ownership.

class Widget {
 public:
    Widget() : title_("") {}
    ~Widget() {}

    void SetTitle(std::string title);

 private:
    std::string title_;
};

class Window {
 public:
    Window() {}
    ~Window() {}

    void AddWidget(Widget* widget);

 private:
    std::vector<Widget*> widgets_;
};

What is the correct approach to solve this problem? Is it fine to just always use shared pointers when writing a library, because I do not know the context? Should I just use raw pointers and make the memory management the application's problem? Supporting both pointer types (shared and unique pointer) would probably blow up the code.

1

There are 1 best solutions below

1
Caleth On

You don't need shared ownership. Consider scenario #3, where the application doesn't own the widget, it only has a reference to it.

You also don't need the application to know which pointer type you pick, so long as the library is in charge of constructing things.

class Widget {
 public:
    Widget(std::string title = "") : title_(title) {}
    ~Widget() {}

    void SetTitle(std::string title);

 private:
    std::string title_;
};

class Window {
 public:
    Window() {}
    ~Window() {}

    Widget* AddWidget(std::string title) {
        auto widget = widgets_.emplace_back(std::make_unique<Widget>(title));
        return widget.get();
    }

 private:
    std::vector<std::unique_ptr<Widget>> widgets_;
};