correct Inheritance/class structure - c++

i want to write a library for linear program solving. Thereby several solvers such as cplex or gurobi are used. What i already have is an interface for each of them (all containing the same functions wrapping them to solver specific code).
Now I want to have a class 'LinearProgram' which can be instantiated e.g. by LinearProgram("cplex") which then invokes the cplex solver.
My first idea was to use a super class 'solver' which is a base class of all solver interfaces containing the respective functions as virtual declarations. But then I get an abstract class which can not be instantiated.
So in LinearProgram i wanted to have a variable Solver which is instantiated depending on the string given in the constructor.
I'm sure a proper solution is quite obvious, but all I can think about in the moment is not satisfying.
Thanks for your help.

This illustrates what you describe:
class Solver {
...abstract base
};
class SolverFactory {
public:
Solver* NewSolverWithName(const std::string& pSolverName);
};
class LinearProgram {
public:
LinearProgram(const std::string& pSolverName) :
d_solver(SolverFactory::NewSolverWithName(pSolverName)) {
}
private:
some_auto_pointer<Solver> d_solver;
};
class cplex_Solver : public Solver {
...
static std::string Name();
};
Solver* SolverFactory::NewSolverWithName(const std::string& pSolverName) {
if (pSolverName == cplex_Solver::Name()) {
return new cplex_Solver();
}
...
}

This is a job for two different design patterns combined.
The first is the Envelope Letter pattern, and the second is the Strategy Pattern.
Keep on with the base class that you currently have and make a derived class that simply forwards the call to an embedded pointer to the base class. The derived class is now something you can freely pass around by value.
The base class could also contain a static member function that returns a pointer to the base class. This static member function would allow you to instantiate a derived class by using a string name to look it up. That provides a convenient way to select an algorithm at runtime.
But people who knew which derived class (which strategy) they wanted could just create one with 'new' and stuff it inside an instance of the envelope class.
You can optionally do away with the envelope class if you decide to just use a shared_ptr to the base class instead.

Related

Override pure virtual function with different parameter of derived type

There are a lot of questions about this topic, but however, I didn't find the solution for my following question:
I have the following classes:
1) The pure virtual class
class Employee {
private:
vector<Employee> vec_employee;
public:
Employee() {};
virtual ~Employee() {};
virtual void set_vec_subordinate(vector<Employee> vec_employee) = 0;
};
2) A derived class
class Worker : Employee{ private: public: };
3) Another derived class which should override the pure virtual method from Employee
class Manager : Employee {
private:
public:
inline void set_vec_subordinate(vector<Worker> vec_employee) override { this->set_vec_subordinate(vec_employee); };
};
What I try to achieve is to override the pure virtual method but use a "different" parameter. So still new to C++ but I think there should be a way to do so, especially because the other parameter is from type Worker which is a derived class from Employee.
There is no way to do exactly what you plan to do (and there is good reason for that).
Your code is also inherently broken, as you use the type vector<Employee>, which requires objects of type Employee - which cannot exist, as Employee is an abstract class. You may wish to use a vector of a reference type, e.g., vector<shared_ptr<Employee>> instead. (The rest of this answer glosses over this fact to make it more readable.)
Note also that void Manager::set_vec_subordinate(vector<Worker> vec_employee) override { this->set_vec_subordinate(vec_employee); }; would cause an infinite loop (probably resulting in a stack overflow) when called, as it will just keep calling itself.
The class Employee has a contract with its users, that says the following code must be valid (assuming given get_boss and get_workers functions):
Employee& boss = get_boss();
vector<Employee> subordinate_vec = get_workers();
boss.set_vec_subordinate(subordinate_vec);
Now, this might not make any semantic sense for your application, but the syntax of the programming language means that this must be possible. Some programming languages (not C++!) allow covariant calls similar to this:
Employee& boss = get_boss();
vector<Worker> subordinate_vec = get_workers();
boss.set_vec_subordinate(subordinate_vec); // Invalid C++: `vector<Worker` cannot be converted to `vector<Employee>` implicitly
While it is indeed possible to create a container in C++ that behaves in a way so that this use is possible, it is easier to deal with it is by making the set_vec_subordinate function a template that requires an arbitrary container of objects that are implicitly convertible or derived from Employee - and then just converting the objects during the copy operation (since the vector is not movable in that case anyway).
The second idea is that it should be possible to change the signature of a function when overriding it. This is kind of possible in C++ by implementing the base case (which needs to be binary compatible with - a.k.a. equal to - the signature of the Employee version, as it will be called for that case as well) and then adding additional overloads. For example, you could do something along the lines of:
class Manager : Employee {
private:
public:
inline void set_vec_subordinate(vector<Employee> vec_employee) override { this->vec_employee = std::move(vec_employee); };
inline void set_vec_subordinate(vector<Worker> const& vec_worker) {
vec_employee = std::vector<Employee>(vec_worker.begin(), vec_worker.end()); // copy convert all elements
};
};

Identifying which Base Class shared_ptr has been passed into a Super Class shared_ptr vector

I am working on a C++ project, specifically implementing a shunting yard algorithm.
I have a function that creates a vector of shared_ptr's of type super class, but the classes that are being pushed into this vector are all base class shared_ptrs.
I then need to take this vector and pass it into another function and carry out different logic for each element of the vector in a for loop. The logic that I carry out, however, depends on which base class is present in each element of the vector.
So basically what I don't know is how to identify which type of base class is in each element of the vector. When I debug they are all coming out as type super-class.
So generally I'd like to do something like this:
if(vectorElement == baseClass)
{
//do some logic
}
Or if there is some different method of carrying this out which I'm missing I'd be interested in carrying that out.
There are many solutions to your problem, frankly is the almost most common problem in OOP.
The most obvious is the virtual function doing different things in different classes:
class SuperClass {
public:
virtual void doSomething(/*someArgsIfNeeded*/) {
// some base implementation, possible empty
// or just use pure virtual function here
}
};
class SubClass : public SuperClass {
public:
virtual void doSomething(/*someArgsIfNeeded*/) {
// some base implementation
}
};
Then use it as follows:
int SomeArgs;
std::vector<std::shared_ptr<SuperClass>> objects;
for (auto it = objects.begin(); it != objects.end(); ++i)
it->doSomething(/*someArgsIfNeeded*/);
Other more sophisticated solution is to use visitor pattern.
It is considered a bad practice to use casting (dynamic_cast), so always search for more OO solutions than casting, like these two I presented above.
Off the top of my head, a simple solution would be to have a function in the base class, that returns an int signifying which class it is. And in each of the derived classes, override this function to return different values. You could use that value to determine which class is being stored in the vector
Edit: And Generally class specific details are to be left in the class, which is the point of polymorphism. Try to do the derived class specific calculations as an overided member function within each class, and use that just to fetch the value forgoing the need for large for loops (for each new derived class) outside.

Writing polymorphic class data to a file?

So I have these classes. There's one base class, but it has/will have lots and lots of derivatives, and those derivative classes will be able to have derivatives as well. I'd like to be able to have a function that writes their binary data to a file, but I'm not sure how to do this with lots and lots of derived classes.
I was thinking something along the lines of:
void writeData(ofstream & _fstream)
{
_fstream.write()//etc..
}
But then each derived class that implemented this method would have to write all of it's parent class's data, and that would be duplicating a lot of code.
What's the best way to do this without rewriting all of the previously written writeData() code?
You can call the base class implementation from the derived class implementation:
void Derived::writeData(ofstream & _fstream)
{
// Base class writes its data
Base::writeData(_fstream);
// now I can write the data that is specific to this Derived class
_fstream.write()//etc..
}
Derived class can call base write methods to avoid code duplication. In fact, that may be the only way to go if some parent's data is private but still is indirectly used.
If you want to avoid re-engineering all the derived class' implementation of the serialization functions, you can go in the other direction, from the base to the derived classes:
In your base class provide a non-virtual function to start the serialization process. Client code calls this function via a pointer (or reference). Also provide a virtual function that does the serialization for the subclass. Call that function from the base class' Serialize function.
(EDIT) If you want to provide default functionality for serializing the subclasses, but still want to be able to provide specialized functionality for specific cases, then the function that serializes the subclasses need not be pure virtual. However, by my reading of your OP it seemed to me that every subclass would need to be required to provide this functionality. To model that requirement, I have made the DoSerialize function pure virtual here.
Example:
class Base
{
public:
void Serialize() const;
virtual void DoSerialize() = 0;
};
class Derived : public Base
{
public:
void DoSerialize() { /* MAGIC HAPPENS */ };
};
void Base::Serialize() const
{
/* .. do serialization of base class here, or at the end -- whichever is appropriate .. */
this->DoSerialize(); // serialize the derived class
}
/* ... */
Base* GetObject()
{
/* ... */
}
int main()
{
Base* obj = GetObject();
obj->Serialize();
}
Ultimately, it is the responsibility of each derived class to make sure that it has been serialized properly. A derived class may need to serialize some data before or after the base class, depending on its purpose. It may also want to totally override the way the base class data is serialized.
Look at it this way - the function being performed here is serialization and de-serialization. The critical thing here is that it needs to be performed correctly. Therefore, the only class that is in a good position to do this is the one with complete knowledge. In other words, its your derived class.
So, there are times when you will have to call Base::writeData(), but whether or not you do that should be left totally up to the derived class. Remember, what you want is for your class hierarchy to satisfy some basic design principles. Once you've got that, it should be relatively easy.

Static method definition delegated to derived class (c++)

Last year I saw some source code (C++) where its author declares static function in base class, but leaves its definition to derived class. I remember there was constraint that only one derived class was permitted to define aforementioned static function.
I know that it is impossible to override static methods, but this trick is exactly what I need. I just can't make it work in my code :) Does anyone know about this feature?
Lets look why this would be useful. Suppose we have some base class (Shape), and its derived classes (Circle, Triangle...). Suppose Shape is part of my core architecture, and derived classes are treated as plugins. I don't want to change my core architecture in future. So we have:
class Shape
{
//other stuff here
static Shape* Factory();
}
class Circle:Shape
{
//other stuff here
static Shape* Factory();
}
Shape is sort of abstract class, and it will not implement Factory method. Method is implemented by one (and only one) of the derived classes. In implementation derived class will return new instance of itself, so it is just a factory method. This trick allowed its author to use this static method in client class in following way:
class Client
{
public Shape* shape;
public Client();
//other stuff here
}
In implementation of constructor he had something like:
Client::Client()
:shape(Shape::Factory())
{
}
This way he was able to instantiate "right" shape derivation without changing core classes in engine. When he wanted some other shape to be used in core classes he just had to define static Factory method in that derived class (and to remove the existing one in other derived class).
This way we have some sort of "static polymorphism". I can't find anything about this technique on the web. Does it even have a name? I am especially interested if something like this could be achieved in C# language? :)
Thanks in advance, and sorry for my bad English.
What it sounds like you are trying to do is a bit messy in my opinion. It feels like a combination of a Factory class, a Singleton and then trying to squish them all back into your result class hierarchy.
The simplest (not necessarily the best) solution I can think of is forget about having either Circle::Factory() or Shape::Factory() and just have a free function called get_default_shape().
class Shape
{
};
class Circle: public Shape
{
};
Shape * get_default_shape()
{
return new Circle;
}
Client::Client()
:shape(get_default_shape())
{
}
The nice bit about this is that its only the implementation of get_default_shape that needs to include Circle.h, all the definition needs is a forward declaration of the Shape class.
Hmm. I have not seen exactly what you describe. It could be that the piece of code you refer to defined the base class static function in the cpp file containing your derived class.
// definition of Circle class
.....
Shape* Shape::Factory()
{
return new Circle();
}
This is not useful in this example but it could be a useful trick if you want to hide the implementation of a class and only publish an abstract base class (to reduce compile time dependencies). It won't work if the base and derived classes are not in the same dll/exe.
Similar things can be achieved in C# by using an IOC framework, with generics, or by registring a factory delegate in your base class. I tend to prefer generics and delegates.

Make object by its name

is it possible to return exemplar of object using passed type name (string) in c++?
I have some base abstract class Base and a few derivates. Example code:
class Base
{
/* ... */
};
class Der1 : public Base
{
/* ... */
};
class Der2 : public Base
{
/* ... */
};
And I need function like:
Base *objectByType(const std::string &name);
Number of derivates classes are changeable and I don't want to make something like switching of name and returning by hands new object type. Is it possible in c++ to do that automatically anyway?
p.s. usage should looks like:
dynamic_cast<Der1>(objectByType("Der1"));
I need pure c++ code (crossplatform). Using boost is permissible.
There is a nice trick which allows you to write a factory method without a sequence of if...else if....
(note that, AFAIK, it is indeed not possible to do what you want in C++ as this code is generated in the compile time. A "Factory Method" Design Pattern exists for this purpose)
First, you define a global repository for your derived classes. It can be in the form std::map<std::string, Base*>, i.e. maps a name of the derived class to an instance of that class.
For each derived class you define a default constructor which adds an object of that class to the repository under class's name. You also define a static instance of the class:
// file: der1.h
#include "repository.h"
class Der1: public Base {
public:
Der1() { repository[std::string("Der1")] = this; }
};
// file: der1.cpp
static Der1 der1Initializer;
Constructors of static variables are run even before main(), so when your main starts you already have the repository initialized with instances of all derived classes.
Your factory method (e.g. Base::getObject(const std::string&)) needs to search the repository map for the class name. It then uses the clone() method of the object it finds to get a new object of the same type. You of course need to implement clone for each subclass.
The advantage of this approach is that when you are adding a new derived class your additions are restricted only to the file(s) implementing the new class. The repository and the factory code will not change. You will still need to recompile your program, of course.
It's not possible to do this in C++.
One options is to write a factory and switch on the name passed in, but I see you don't want to do that. C++ doesn't provide any real runtime reflection support beyond dynamic_cast, so this type of problem is tough to solve.
Yes that is possible! Check this very funny class called Activator
You can create everything by Type and string and can even give a List of parameters, so the method will call the appropriate constructor with the best set of arguments.
Unless I misunderstood, the typeid keyword should be a part of what you are looking for.
It is not possible. You have to write the objectByType function yourself:
Base* objectByType(const std::string& name) {
if (name == "Der1")
return new Der1;
else if (name == "Der2")
return new Der2;
// other possible tests
throw std::invalid_argument("Unknown type name " + name);
}
C++ doesn't support reflection.
In my opinion this is the single point where Java beats C++.
(ope not to get too many down votes for this...)
You could achieve something like that by using a custom preprocessor, similar to how MOC does for Qt.