does this make sense as a way to uniquely identify objects and create them on demand? I want to have this 'registerDerived' option because I want to have a set of default objects pre-registered and then let additional ones be created and registered, all at compile time but I can't figure out how to do this registering at compile time so it's runtime
the map & reverse map at the end are just so a list of identifiers can be displayed and then fed back in to create the correct object
struct Base {
virtual ~Base() = default;
};
struct A : Base {
static std::unique_ptr<Base> create() {
return std::make_unique<A>();
}
};
struct B : Base {
static std::unique_ptr<Base> create() {
return std::make_unique<A>();
}
};
class BaseFactory {
public:
std::unique_ptr<Base> create(std::type_index idx) {
return mapping[idx]();
}
void registerDerived(std::type_index idx, std::function<std::unique_ptr<Base>()> create) {
mapping[idx] = create;
}
std::map<std::type_index, std::function<std::unique_ptr<Base>()>> mapping;
};
int main()
{
BaseFactory factory;
factory.registerDerived(std::type_index(typeid(A)), A::create);
factory.registerDerived(std::type_index(typeid(B)), B::create);
std::map<std::string, std::type_index> name_to_config = {
{ "A", std::type_index(typeid(A)) },
{ "B", std::type_index(typeid(B)) },
};
//generate the reverse map
std::map<std::type_index, std::string> config_to_name;
for(auto &pair : name_to_config)
assert(config_to_name.insert({pair.second, pair.first}).second);
return 0;
}