I would like to get return type of each function stored in a container. I have tried std::any and std::variant but i couldn't figure this out. Details below:
#include <random>
#include <vector>
#include <functional>
using namespace std;
class Base
{
public: virtual void test() { }
};
class Derived1 : public Base
{
public: virtual void test() { }
};
class Derived2 : public Base
{
public: virtual void test() { }
};
int main ()
{
std::vector<std::function < Base(void)>> b;
b.push_back([&]() { return Derived1(); });
b.push_back([&]() { return Derived2(); });
b.push_back([&]() { return Base(); });
std::shuffle(b.begin(), b.end(), std::default_random_engine {});
for (auto fn : b)
{
// Here I would like to reach the derived classes from "fn" somehow and use it like "new Derived1"
//decltype(fn)::result_type ----------> this gives me Base only but i want the derived as well
}
}
I have managed to solve this two different ways.
First way:
int main()
{
std::vector<std::function<Base& ()>> b;
b.push_back([]() -> Base& { static Derived1 d1; return d1; });
b.push_back([]() -> Base& { static Derived2 d2; return d2; });
b.push_back([]() -> Base& { static Base b; return b; });
std::shuffle(b.begin(), b.end(), std::default_random_engine{});
for (auto& fn : b)
{
if (auto derived1_ptr = dynamic_cast<Derived1*>(&fn()))
{
derived1_ptr->test();
Derived1* var = new Derived1(*derived1_ptr);
var->test();
}
else if (auto derived2_ptr = dynamic_cast<Derived2*>(&fn()))
{
derived2_ptr->test();
Derived2* var = new Derived2(*derived2_ptr);
var->test();
}
}
return 0;
}
Second way:
int main()
{
std::vector<std::function<std::shared_ptr<Base>()>> b;
b.push_back([&]() { return std::make_shared<Derived1>(); });
b.push_back([&]() { return std::make_shared<Derived2>(); });
b.push_back([&]() { return std::make_shared<Base>(); });
std::shuffle(b.begin(), b.end(), std::default_random_engine{});
for (auto fn : b)
{
if (auto derived1_ptr = std::dynamic_pointer_cast<Derived1>(fn()))
{
derived1_ptr->test();
shared_ptr<Derived1> var = std::make_shared<Derived1>(*derived1_ptr);
var->test();
}
else if (auto derived2_ptr = std::dynamic_pointer_cast<Derived2>(fn()))
{
derived2_ptr->test();
shared_ptr<Derived2> var = std::make_shared<Derived2>(*derived2_ptr);
var->test();
}
}
return 0;
}