Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Should C++ abstract factory provide destroy method for constructed objects?

Consider the following interface (dumb pointers are used because we are still in C++98)

class WidgetMaker {
    virtual Widget* makeWidget() = 0;
};

With the following likely implementation

class SpecificWidgetMaker: public WidgetMaker {
    Widget* makeWidget() {
        return new SpecificWidget();
    }
};

Widget is some base class with virtual destructor, SpecificWidget extends it. My colleagues claim that the WidgetMaker interface should contain the following method

virtual void freeWidget(Widget* widget);

Rationale being is that this way we do not force makeWidget implementations to use standard new allocation, they can use custom pool allocator or always return the same global instance in case widget is stateless or whatever.

I feel such design is generally a bad idea - it complicates client code, violates KISS and YAGNI, makes transition (unlikely in our organization in next 20 years) to unique_ptr harder. Should I trust my feelings? What are the cases when free method as part of abstract factory interface is justified?

like image 754
Muxecoid Avatar asked Mar 14 '23 08:03

Muxecoid


1 Answers

A problem with your friend's proposed solution (actually, also with your original one), is that it has an unnecessarily nontrivial protocol. Once you obtain a Widget via makeWidget, you need to remember to deallocate it (either directly, or by calling some method of the factory). This is known to be fragile - it will either break down quickly (causing Widget leaks), or really complicate the client code.

If you look at the interface of std::shared_ptr::shared_ptr(...), you can see that it can take a custom deleter object.

Thus, perhaps you could typedef (or the equivalent) what exactly is a Widget smart pointer:

using WidgetPtr = std::shared_ptr<Widget, ...>

In case you later decide that the factory needs to perform some action when a Widget is deallocated, you can change the typedef to one which uses a custom deleter, and this custom deleter can notify the factory that an object is being deleted.

The main advantage of this is that it removes the onus of remembering to deallocate a Widget from the user.

like image 85
Ami Tavory Avatar answered Apr 29 '23 18:04

Ami Tavory