Я пытаюсь внедрить некоторые игровые классы с использованием языка сценариев. Предположим, что моя основная структура:Прозрачная агрегирование классов
class BaseGameObject {
public:
virtual ~BaseGameObject() { }
};
class DerivedGameObject : public virtual BaseGameObject {
};
И потом, я хочу, чтобы прикрепить информацию о том, как я связать этот класс на движке сценариев. Я хочу, чтобы сохранить единство с ними как можно меньше, так что я закончился с этим шаблоном рисунка:
class ScriptLanguageBinder {
public:
virtual void bind(VM* vm) = 0;
};
template < typename GameObject >
class GameObjectLanguageBinder : public GameObject, public ScriptLanguageBinder {
virtual void bind(VM* vm) {
vm->bind<GameObject>(static_cast<GameObject*>(this));
}
};
template < typename GameObject >
BaseGameObject* gameObjectBuilder() {
return new GameObjectLanguageBinder<GameObject>();
}
Так что есть завод, которые строят «обернут» BaseGameObject и возвращает GameObjectLanguageBinder на месте. Таким образом, остальная часть системы использует результирующий класс как BaseGameObject *, зависимость языка сценария ограничивается набором классов, которые не вредят экосистеме Game, и только мой движок сценария должен знать, что на самом деле это GameObjectLanguageBinder. Это работает очень хорошо, кроме одной точки:
Чтобы получить обратно объект ScriptLanguageBinder из BaseGameObject * Мне нужно сделать это:
ScriptLanguageBinder* binder = dynamic_cast<ScriptLanguageBinder*>(my_game_object);
Что нежелательно, так как я хочу, чтобы выжать все производительности, что я могу из исполнение кода (это движок для мобильных игр, так что да, показатели производительности).
Так что мне было интересно, есть ли какой-либо ненавязчивый, прозрачный способ достичь этого без с использованием динамического приведения. Я думал использовать шаблон посетителя, но этот шаблон является блокировщиком, когда вы хотите расширить классы, которые вы посещаете, поэтому это не выход.
пс: завод ultra более-упрощенный на этом примере.
Примечание: Абсолютно нужен виртуальный деструктор, если вы планируете удалить указатель только на базовый класс. Кстати, это может служить одной виртуальной функцией, в которой вы нуждаетесь. : p – Xeo
Да, я это знаю. Классы arent эти, я просто упростил все здесь :) – scooterman