#include #include #include #include #include #include using std::map; using std::string; using std::cout; using std::cin; using std::vector; using std::endl; using std::runtime_error; class Object { public: virtual string ToString() const = 0; virtual ~Object() = default; }; class Apple : public Object { public: string ToString() const override { return "apple!"; } }; class List : public Object { public: string ToString() const override { return "list"; } }; class YetAnotherId : public Object { public: string ToString() const override { return "yet another identifier"; } }; class Smth : public Object { public: explicit Smth(const std::string& class_id) { class_id_ = class_id; } std::string ToString() const override { return class_id_; } private: std::string class_id_; }; map registered_classes; class Factory { public: static Object *Create(const string &class_id) { if (class_id == "apple") { return new Apple; } else if (class_id == "list") { return new List; } else if (class_id == "yet another identifier") { return new YetAnotherId; } else { if (registered_classes.count(class_id) > 0) { return new Smth(class_id); } else { throw runtime_error("not registered"); } } } static void Register(const string &class_id, Object *(*creator)()) { registered_classes[class_id] = creator; } };