Я пытаюсь реализовать порождающую систему для проекта, в котором у меня есть контейнерный класс (в данном случае это, по сути, мир), который может содержать любой объект мира, для которого существует несколько производных классов.
Поскольку контейнерный класс имеет информацию, относящуюся к созданию экземпляра производного класса (который не нужен внешнему классу, вызывающему метод spawn), я подумал, что имеет смысл использовать шаблонную функцию-член, тип которой является функцией вызываемый определяется как таковой
containerClass.functionName<type>(/*no arguments specifying the type*/);
без шаблонов класса контейнера (поскольку класс содержит несколько типов объектов)
Это может быть моим недоразумением, но нельзя ли взять информацию о типе, которую нужно передать, из значений в скобках (или как они обычно называются <>)?
Следующий (упрощенный) код был моей реализацией такой задачи, учитывая мое понимание шаблонов:
#include <vector>
#include <iostream>
class baseClass {
public:
virtual const char* getName() { return "baseClass"; }
};
class derivedA : public baseClass {
public:
const char* getName() { return "derivedA"; }
};
class derivedB : public baseClass {
public:
const char* getName() { return "derivedB"; }
};
class container {
public:
container() {}
~container() {
for (int i = 0; i < contained.size(); ++i) {
delete contained[i];
}
}
template <typename type> void spawn() {
contained.push_back(new type(/*in my case the container has data with which to initialize the class*/));
}
void printNames() {
for (int i = 0; i < contained.size(); ++i)
std::cout << contained[i]->getName() << std::endl;
}
private:
std::vector<baseClass*> contained;
};
int main() {
container c;
c.spawn<derivedA>();
c.spawn<derivedB>();
c.spawn<derivedA>();
c.printNames();
return 0;
}
Это работает как ожидалось (учитывая модификацию из исходного вопроса), производя
derivedA
derivedB
derivedA
Хотя мне еще предстоит заставить это работать в моем реальном проекте (что дает мне ошибку компоновщика, говорящую о том, что конкретный метод шаблона не существует), мне интересно, является ли это допустимым C ++ и / или хорошей практикой. Есть ли более рекомендуемые способы реализации этого?
Я был бы очень признателен, если бы кто-нибудь объяснил, как лучше всего реализовать такую функцию, желательно не пропуская неиспользованные экземпляры.
В менее профессиональной заметке (которую, я уверен, какой-то пользователь отредактирует ...), я прошу прощения за длину этого вопроса. По той же причине, по которой я представляю, что это может быть повторяющийся пост, я не знаю терминологии, с помощью которой можно лучше объяснить мою ситуацию. Если вы как-то пережили все это, я благодарю вас за терпение!