Here is my issue.
I'm creating my own GUI Api. All the Widgets are in a container which has add and remove functions. The widgets derive from a base widget class. Here is where I'm unsure. I would ideally like a flow like this:
user creates a (desired widget deriving from base class) pointer, the container allocates and manages resources, the user has a pointer to the widget and can make calls to it.
However, polymorphism makes this confusing. How could I get my container to create the right type of new? The issue here is that anyone can create a new widget (like SuperTextBoxWidget) which is why supplying a string and doing a switch would not solve this.
My other quick-fix alternative is to make the user responsible for doing the new, and providing the pointer to the container's add function. But this does not feel idiot proof to me, and it seems odd to have the user do the initial allocation, but then the container manages the rest including erasure.
What would be the best and cleanest way to go about this?
Thanks
just an idea of what I have so far:
class AguiWidgetContainer
{
std::vector<AguiWidgetBase*> widgets;
public:
AguiWidgetContainer(void);
~AguiWidgetContainer(void);
void handleEvent(ALLEGRO_EVENT* event);
int add(AguiWidgetBase *widget);
bool remove(int widgetId);
};
I can think of at least two ways to do this.
1. Provide a template version of add:
template<class T>
int add() {
widgets.push_back(new T);
}
2. Use a factory class:
You can have a base factory class that defines methods to allocate (and possibly also free) widgets. Your users then provide their own subclass of the factory that creates the correct type of widget. For example:
class AguiWidgetFactory {
AguiWidgetBase *createWidget() = 0;
};
class AguiSuperWidgetFactory : public AguiWidgetFactory {
AguiWidgetBase *createWidget() {
return new SuperTextBoxWidget();
}
};
Your add method then takes a factory object as input and uses it to create a new widget.
I would suggest borrowing from COM and making your base widget class a pure virtual interface which includes a function to destroy itself. Then implementers of your widget don't even all have to use the same allocator (important if you ever cross DLL boundaries).
EDIT: Example:
class IWidget
{
public:
virtual Size Measure() = 0;
virtual void Draw(Point) = 0;
//and so on
virtual void Release() = 0;
};
class TextBoxWidget : public IWidget
{
TextBoxWidget() {}
~TextBoxWidget() {}
public:
// implement IWidget functions, etc, etc
static TextBoxWidget* Create() { return new TextBoxWidget(); }
virtual void Release() { delete this; }
};
Now TextBoxWidget can only be created with TextBoxWidget::Create() and released with someTBW->Release(), and always uses new and delete inside the same DLL, guaranteeing that they match.
My other quick-fix alternative is to
make the user responsible for doing
the new, and providing the pointer to
the container's add function. But this
does not feel idiot proof to me, and
it seems odd to have the user do the
initial allocation, but then the
container manages the rest including
erasure.
Why does it feel odd to you?
If a container starts taking responsibility of allocating the objects to be contained, it violats SRP. I would recommend that you design your interfaces to accept pointers to Widget objects that are allocated by users. The container is only responsible for containing/storing/retreiving them.
The user also takes responsibility of deleting the allocated objects.
Most of STL containers work in this way.
Related
I have situation in which I am getting a crash on clearing the memories in destructor. Please see the code below
C++ Code:
class Key{
....
};
Class Object {
...
};
Class E {
private:
vector<Object> m_vector;
};
Class A {
public:
virtual void check()=0;
protected:
hashmap<Key*,E*> myMap;
};
A:~A() {
EMapItr eMapItr = myMap.beginRandom();
for(; eMaptr; ++eMapItr) {
delete eMapItr.value();
}
E:~E() {
m_vector.clear();
}
class B: public A {
public:
virtual void check()
private:
DB* db;
}
void B::check() {
db->create(&myMap);
}
QT Code:
class MyQtAction {
public:
void act() ;
private:
GUIObject* guiWindowObject
};
MyQtAction::act() {
A* aobj = new B();
if(!guiWindowObject) {
guiWindowObject = new GUIObject(aobj);
}
};
class GUIObject:public QWidget {
private:
A* guiAobj;
};
GUIObject:GUIObject(A* obj) {
guiAobj= obj;
}
GUIObject:~GUIObject {
}
Now Can you please where shall I delete the point of A class because object of A is created multiple times
Since you're using Qt, I'd suggest your leverage on its very powerful "Object Trees & Ownership" model that comes for free with it:
QObjects organize themselves in object trees. When you create a
QObject with another object as parent, it's added to the parent's
children() list, and is deleted when the parent is.
http://doc.qt.io/qt-5/objecttrees.html
derive your classes from QObject, and make them use/require a QObject as parent parameter.
then, at instanciation, specify the parent object (this is why there
is a "parent" parameter all over the place in Qt's constructors
documentation),
no more delete, enjoy automagic deletion of child, grand child,
grand-grand child etc when the parent is deleted / goes out of scope.
You can use the QObject::dumpObjectTree() to visualise the parent/child tree at run time.
http://doc.qt.io/qt-5/qobject.html#dumpObjectTree
Now, there can be some tricky situations (see the doc above) which may require manual explicit delete, but in my experience 95% of the time it's fine - and in any case much less error prone than handling this yourself as your application grow big and complex. If you use Qt, you definitely want to use this. It's a great feature of the framework.
EDIT:
Now, about the context of your development and "is it C++ or is it Qt"?
If you want to learn C++ the hard and good way (and just add a bit of
fun with a few Qt graphical widgets), then you must understand the
destructors and be able to to handle it by yourself.
On the other hand, if you want to create a serious Qt application,
then you must embrace the Qt framework as a whole, and this
parent/child QObject fundamental base class, from which all others Qt's
class are derived is fundamental and oh-so-useful. There are a couple
of others root fundamental Qt concept, such as No Copy Constructor or Assignment
Operator, with
its very important consequence that you'll use pointers everywhere,
and its rationale
here, or Qt's
"no exceptions" motto, explained
here, from
"historical and practical reasons" to quote the documentation, and if
I'm not mistaken was not supported at all before Qt>=5. When doing
Qt, do full Qt. The hardcore C++, thought available, is buried under the
surface.
You should delete it in act(). Otherwise you may lose trace of it. It is not a good idea to initialize memory and then transfer the pointer to an object (unless of course the situation requires it). My advice is to move the new for A in the GUIObject's constructor. When GUIObject is deleted you can safely eliminate A without running into a double memory free.
Something like this:
class GUIObject {
A* aobj;
public:
GUIObject();
~GUIObject();
};
GUIObject::GUIObject()
{
A* aobj = new B();
}
GUIObject::~GUIObject()
{
delete aobj;
}
This following question is a bit hard for me to formulate, but please bear with me, and let me know if I can help in clearing anything up.
I am writing a general-purpose simulation for 3D shapes. I am using a base class:
class Shape{
public:
...
virtual double return_volume() =0;
private:
vector<double> coordinates;
...
};
Now, since I don't know what shape the user will choose, I derive several classes from this. (e.g.: Sphere, Cube, Tetrahedron, etc.)
So far, everything is fine.
The main problem comes in the form that I have a Controller class, which launches and operates the simulation. As a private member, it should have a vector of multiple shapes (all of the same type. e.g.: 15 spheres, or 10 cubes, etc.)
class SimulationControl{
public:
void runsimulation();
private:
vector<Shape> all_shapes;
...
};
I wanted to simply initialize this private member with a non-default constructor.
Now, before I knew what I had done, Eclipse already told me that "The type 'Shape' must implement the inherited pure virtual method 'Shape::return_volume'"
I understand the error message and my mistake, of course, but I still don't understand how I can solve it.
What I would love to be able to do is to leave the type of vector undefined, and then simply create it via the constructor with the correct derived class at runtime, when I know which type of simulation the user chose.
Is is somehow possible to do that? Thanks
I'm not going to jump on the bandwagon and suggest using pointers in your container, whether smart or dumb. This is the perfect opportunity to use the PIMPL idiom.
The idea is that the class is simply a wrapper for the actual implementation, and calls a pointer to another object when a call is made to it. The pointer contained within the wrapper can be polymorphic so that it can implement the functions however it sees fit.
class Shape{
public:
Shape() { pImpl = NULL; }
Shape(const Shape& from) { pImpl = from.pImpl->clone(); }
~Shape() { delete pImpl; }
Shape& operator=(const Shape& from) { pImpl = from.pImpl->clone(); }
...
double return_volume() { return pImpl->return_volume(); }
private:
ShapeImpl * pImpl;
...
};
class ShapeImpl{
public:
...
virtual ShapeImpl* clone() const =0;
virtual double return_volume() =0;
private:
vector<double> coordinates;
...
};
Because the Shape class contains a pointer you'll need to implement the rule of three and create a destructor, copy constructor, and operator=. The defaults for the copies will certainly do the wrong thing - they'll only copy the pointer value without creating a new copy of the pimpl object to go with them. Since a vector copies elements around these functions are certain to get called.
Use (smart) pointers.
You cannot instantiate an abstract class, and even if you could, that would probably not be what you want, since you wouldn't be able to create aliases of those shapes.
You should change the definition of your SimulationControl class into something more similar to this (assuming shared ownership for your shapes here - if SimulationControl is the only owner of your shapes, rather use unique_ptr instead of shared_ptr):
#include <memory>
class SimulationControl {
public:
void runsimulation();
private:
std::vector<std::shared_ptr<Shape>> all_shapes;
...
};
Then, you could create instances of your shapes and add them to the all_shapes collection as follows (supposing MyShape is a concrete, default-constructible class derived from Shape):
std::shared_ptr<MyShape> pShape = std::make_shared<MyShape>();
pShape->set_vertices(...); // I guess the class will have a member function
// that allows setting the shape's vertices...
all_shapes.push_back(pShape);
You can only do polymorphism by pointer or reference. Try using vector<Shape*>.
Now that you are using pointers you'll have to manage the memory for them, but that is another set of questions. Try to use smart pointers if you can, or be very careful if you can't. If you are using C++11, std::vector<std::unique_ptr<Shape>> might fit the bill for you.
I recently found an example of using static member functions in pure abstract classes to initialize pointers to objects of its derived classes.
I was wondering, if it's a design pattern or if it's a good programming practice? The code below is only an ilustration (e.g. both the defineRectangle() and defineCircle() member
functions):
class Shape;
typedef std::unique_ptr<Shape> shape_ptr;
class Shape{
public:
Shape(){};
virtual ~Shape(){};
virtual void draw() const = 0;
virtual float area() const = 0;
virtual shape_ptr clone() const = 0;
virtual shape_ptr create() const = 0;
static shape_ptr defineRectangle(int, int );
static shape_ptr defineCircle(float);
};
shape_ptr Shape::defineRectangle(int height, int width){
shape_ptr ptrRectangle = shape_ptr(new Rectangle(height, width));
return (ptrRectangle);
}
shape_ptr Shape::defineCircle(float radius){
shape_ptr ptrCircle = shape_ptr(new Circle(radius));
return (ptrCircle);
}
The final goal is to define a container of derived classes. For instance:
std::vector<std::unique_ptr<Shape> > vect;
and then we could add the derived classes in the container by either calling the static member functions of the Shape class:
vect.push_back(Shape::defineCircle(10));
vect.push_back(Shape::defineRectangle(5, 4));
or directly without any interface:
vect.push_back(std::unique_ptr<Shape>(new Circle(10)));
vect.push_back(std::unique_ptr<Shape>(new Rectangle(5,4)));
Which of both two ways of adding a derived class in a container should be preferred and why?
The full code can be found in the following link.
Any lights on it are really welcomed ;-)
I was wondering, if it's a design pattern or if it's a good programming practice?
Yes, it's a variation on the factory pattern.
Basically put, it allows you to have a single method, that depending on the arguments to that method, will dispatch the dynamic creation of the correct derived object type. This allows you to use the same "factory" function in your code, and if there are any changes or additions to the underlying objects that the factory method creates, you do not have to change the code that is actually calling your "factory" function. Thus it's a form of encapsulation that isolates any changes for object creation to the segment of the code that is behind the "factory", not the code calling the "factory". For instance, using a factory, it's relatively trivial to add new types that the factory-method can create, but none of the previous code that is making a call to the factory has to change. You merely need to create a new derived class for the new object you want to create, and for any new code that desires that new object, you pass the correct new arguments. All the old arguments still work, and there are not changes that need to take place in the code with regards to returned pointer-types, etc.
The reason for using smart-pointers with the factory is to avoid memory leaks that can occur when pointer-ownership is ambiguous. For instance the factory has to return a pointer since it is dyanmically creating the object. The question then becomes who cleans up the pointer in order to avoid either dangling pointers or memory leaks? Smart pointers clear up this ownership problem, and guarantee that memory is not either inadvertently cleaned up when other objects are still pointing to that memory, or that the memory is not simply lost because the last pointer to that memory location goes out of scope without having delete called on it.
I'd advise against putting factory methods in the base class because, technically, Shape knows nothing about Rectangle or Circle. If you add a new shape, such as Donut, then what will you do? Add a new factory method to Shape? You'll clutter the interface in no time. So, IMO, the second method would be better.
If you want to reduce the verbosity of having to create shape_ptr a every time, you could always move the factory methods to the appropriate subclass:
class Circle : public Shape
{
// ...
public:
static shape_ptr make(float radius)
{
return shape_ptr(new Circle(radius));
}
};
// ...
vect.push_back(Circle::make(5.0f));
Since there is std::unique_ptr, I assume the compiler supports C++11. In that case, let me offer the third option:
vect.emplace_back(new Circle(10));
vect.emplace_back(new Rectangle(5,4));
(About .emplace_back: push_back vs emplace_back)
With this you don't need to repeat the shape_ptr, and you don't need to declare a new factory method to Shape whenever you add a new subclass.
Edit: In C++14, you can use std::make_unique to get rid of the raw new call.
vect.emplace_back(std::make_unique<Circle>(10));
vect.emplace_back(std::make_unique<Rectangle>(5, 4));
I'm developing a GUI library with a friend and we faced the problem of how to determine whether a certain element should be clickable or not (Or movable, or etc.).
We decided to just check if a function exists for a specific object, all gui elements are stored in a vector with pointers to the base class.
So for example if I have
class Base {};
class Derived : public Base
{
void example() {}
}
vector<Base*> objects;
How would I check if a member of objects has a function named example.
If this isn't possible than what would be a different way to implement optional behaviour like clicking and alike.
You could just have a virtual IsClickable() method in your base class:
class Widget {
public:
virtual bool IsClickable(void) { return false; }
};
class ClickableWidget : public Widget
{
public:
virtual bool IsClickable(void) { return true; }
}
class SometimesClickableWidget : public Widget
{
public:
virtual bool IsClickable(void);
// More complex logic punted to .cc file.
}
vector<Base*> objects;
This way, objects default to not being clickable. A clickable object either overrides IsClickable() or subclasses ClickableWidget instead of Widget. No fancy metaprogramming needed.
EDIT: To determine if something is clickable:
if(object->IsClickable()) {
// Hey, it's clickable!
}
The best way to do this is to use mixin multiple inheritance, a.k.a. interfaces.
class HasExample // note no superclass here!
{
virtual void example() = 0;
};
class Derived : public Base, public HasExample
{
void example()
{
printf("example!\n");
}
}
vector<Base*> objects;
objects.push_back(new Derived());
Base* p = objects[0];
HasExample* he = dynamic_cast<HasExample*>(p);
if (he)
he->example();
dynamic_class<>() does a test at runtime whether a given object implements HasExample, and returns either a HasExample* or NULL. However, if you find yourself using HasExample* it's usually a sign you need to rethink your design.
Beware! When using multiple inheritance like this, then (HasExample*)ptr != ptr. Casting a pointer to one of its parents might cause the value of the pointer to change. This is perfectly normal, and inside the method this will be what you expect, but it can cause problems if you're not aware of it.
Edit: Added example of dynamic_cast<>(), because the syntax is weird.
If you're willing to use RTTI . . .
Instead of checking class names, you should create Clickable, Movable, etc classes. Then you can use a dynamic_cast to see if the various elements implement the interface that you are interested in.
IBM has a brief example program illustrating dynamic_cast here.
I would create an interface, make the method(s) part of the interface, and then implement that Interface on any class that should have the functionality.
That would make the most sense when trying to determine if an Object implements some set of functionality (rather than checking for the method name):
class IMoveable
{
public:
virtual ~IMoveable() {}
virtual void Move() = 0;
};
class Base {};
class Derived : public Base, public IMoveable
{
public:
virtual void Move()
{
// Implementation
}
}
Now you're no longer checking for method names, but casting to the IMoveable type and calling Move().
I'm not sure it is easy or good to do this by reflection. I think a better way would be to have an interface (somethign like GUIElement) that has a isClickable function. Make your elements implement the interface, and then the ones that are clickable will return true in their implementation of the function. All others will of course return false. When you want to know if something's clickable, just call it's isClickable function. This way you can at runtime change elements from being clickable to non-clickable - if that makes sense in your context.
I'm experiencing a challenging problem, which has not been solvable - hopefully until now. I'm developing my own framework and therefore trying to offer the user flexibility with all the code complexity under the hood.
First of all I have an abstract base class which users can implement, obviously simplified:
class IStateTransit
{
public:
bool ConnectionPossible(void) = 0;
}
// A user defines their own class like so
class MyStateTransit : public IStateTransit
{
public:
bool ConnectionPossible(void){ return true; }
}
Next, I define a factory class. Users can register their own custom state transit objects and refer to them later by simply using a string identifier they have chosen:
class TransitFactory : public Singleton<TransitFactory>
{
public:
template<typename T> void RegisterStateTransit(const string& name)
{
// If the transit type is not already registered, add it.
if(transits.find(name) == transits.end())
{
transits.insert(pair<string, IStateTransit*>(name, new T()));
};
}
IStateTransit* TransitFactory::GetStateTransit(const string& type) const
{
return transits.find(type)->second;
};
private:
map<string, IStateTransit*> transits;
}
Now the problem is (probably obviously) that whenever a user requests a transit by calling GetStateTransit the system currently keeps returning the same object - a pointer to the same object that is. I want to change this.
PROBLEM: How can I return a new (clone) of the original IStateTransit object without the user having to define their own copy constructor or virtual constructor. Ideally I would somehow like the GetStateTransit method to be able to cast the IStateTransit object down to the derived type it is at runtime and return a clone of that instance. The biggest hurdle is that I do not want the user to have to implement any extra (and probably complex) methods.
4 hours of Googling and trying has led me nowhere. The one who has the answer is a hero!
The problem is that you don't have the type information to perform the clone as you only have a pointer to base class type and no knowledge as to what derived types have been implemented and are available.
I think there's a reason that 4 hours of googling haven't turned anything up. If you want IStateTransit to be cloneable you have to have an interface where the derived class implementer provides some sort of clone method implementation.
I'm sorry if this isn't what you wanted to hear.
However, implementing a clone method shouldn't be a big burden. Only the class implementor knows how a class can be copied, given a correct copy constructor, clone can be implemented for a leaf-node class like this:
Base* clone() const
{
return new MyType(*this);
}
You could even macro-alize it; although I wouldn't.
If I understand the problem correctly, you shouldn't insert new T -s into the map, but rather objects that create new T-s.
struct ICreateTransit
{
virtual ~ICreateTransit() {}
virtual IStateTransite* create() const = 0;
};
template <class T>
struct CreateTransit: public ICreateTransit
{
virtual IStateTransit* create() const { return new T(); }
};
And now insert:
transits.insert(pair<string, ICreateTransit*>(name, new CreateTransit<T>()));
And retrieve "copies" with:
return transits.find(type)->second->create(); //hopefully with error handling
It shouldn't be impossible to modify StateTransit<T> so it holds a T of which to make copies of, should the default one not do.
I think the general name for techniques like this is called "type erasure" (derived types "remember" particular types, although the base class is unaware of those).
This problem to me sounds that the abstract factory pattern might be of help. Using this pattern the libraries client can define how your framework builds its types. The client can inject his own subclass of the factory into the framework and define there what types should be build.
What you need is (additionaly)
A base class for the factory
As a client: Derive a concrete factory
A way to inject (as a client) a subtype of the factory into the framework
Call the factory metods to create new types.
Does this help you?