Я пишу физический движок на C ++, и я остановился, а именно, как я должен проектировать иерархию классов. Что меня особенно беспокоит, так это World
а также Body
классы. Body
следует раскрыть некоторые детали World
тот World
тогда можно работать дальше. Но в то же время я не хочу, чтобы пользователи имели доступ ко всем этим свойствам Body
, Но я все еще хочу, чтобы пользователи двигателя могли изменять некоторые вещи в теле. Например, его позиция. Как бы вы структурировали это с точки зрения классов?
Определить interface
(то есть чисто виртуальный класс), который определяет, какие функции вы хотите получить от Body
, Есть Body
реализовать этот интерфейс.
Разрешить этот интерфейс, а не Body
использоваться из World
,
Эта модель называется состав.
Недавно я решил похожую проблему, введя специальный интерфейс для операций с ограниченным доступом и наследуя protectedly от него. Как это:
struct RestrictedBodyFunctions
{
virtual void step() = 0;
virtual Body& asBody() = 0;
};struct Body : protected RestrictedBodyFunctions
{
static std::unique_ptr<Body> createInWord(World &world)
{
auto Body = std::unique_ptr<Body>{new Body()};
world.addBody(*body); // cast happens inside Body, it's accessible
return std::move(body);
}
std::string getName() const;
void setName(std::string name);
protected:
void step() override
{ /*code here*/ }
Body& asBody() override
{ return *this; }
};struct World
{
void addBody(RestrictedBodyFunctions &body)
{
m_bodies.push_back(&body);
}
void step()
{
for (auto *b : m_bodies)
{
myLog << "Stepping << " b->asBody().getName() << '\n';
b->step();
}
}
private:
std::vector<RestrictedBodyFunctions*> m_bodies;
};
Таким образом, пользователи могут создавать Body
объекты, использующие createInWorld
, но они получают только ручку (публичную часть) Body
, в то время как World
получает свою ручку RestrictedBodyFunctions
,
Другой вариант, который у вас есть, — отменить вышеуказанную идею — предоставить ограниченный публичный интерфейс. PublicBody
, и имеют Body
вытекают из PublicBody
, Ваши внутренние классы будут использовать полный Body
, пока заводские функции проверяют только PublicBody
ручки доступны для клиентов. Эта альтернатива является более простой конструкцией, но обеспечивает меньший контроль над тем, кто может получить доступ ко всем функциям.