Организация взаимосвязанных объектов - PullRequest
1 голос
/ 07 декабря 2011

Это общий вопрос, я не знаю, относится ли он к программированию или StackOverflow.

Я пишу небольшую симуляцию. Не углубляясь в его детали, учтите, что здесь задействованы многие виды идентичностей. Они соответствуют объекту, так как я использую язык ООП.

  • Есть Парни , которые населяют мир, моделируемый
  • Есть Карты
  • На карте много Лотов , которые представляют собой участки земли с некоторыми характеристиками
  • Есть Племен (ребята принадлежат к племенам)
  • Существует универсальный класс с именем Position для определения местоположения элементов
  • Боты контролируют племена, которые перемещают парней вокруг
  • Существует Мир , который представляет симулированный мир

и т. Д.

Если бы моделируемый мир был заложен в качестве базы данных, объекты были бы таблицами с большим количеством ссылок, но в памяти я должен использовать другую стратегию. Так, например, у Племени в качестве свойства есть массив Парней, в мире есть массив Ботов, Племен, Карт. Карта имеет словарь, ключ которого - позиция, а значение - лот. У парня есть позиция, в которой он стоит.

То, как я устанавливаю такие связи, в значительной степени произвольно. Например, у меня может быть массив парней в мире, или массив парней за лот (парни стоят на клочке земли), или массив парней на бот (с парнями, контролируемыми ботом).

Для этого я также должен обойти множество объектов. Например, бот должен иметь информацию о карте и парнях противника, чтобы решить, как их перемещать.

Как уже говорилось, в базе данных я бы имел таблицу Guys, связанную с таблицей Lots (с указанием ее позиции), с таблицей Tribe (с указанием, к какому племени она принадлежит), и поэтому было бы также легко запросить "All" ребята в позиции [1, 5] ". «Все парни из племени 123». «Все парни, контролируемые ботом B, стоящие на лоте b34, не принадлежащие к племени 456» и т. Д.

Я работал с API, где для получения простейшей информации вам нужно было создать экземпляр CustomerContextCollection и передать его в CustomerQueryFactory, чтобы вернуть CustomerInPlaceQuery ... Когда люди критикуют ООП и приводят подробные абстракции, которые скоро пахнут смешно , это то, что я имею в виду. Я хочу избегать таких вещей и необходимости использовать глубокие абстракции и (анти-паттерн) абстрактные контексты.

Вопрос заключается в следующем: каков предпочтительный, чистый способ управления объектами и коллекциями объектов, которые тесно связаны между собой несколькими способами?

Ответы [ 2 ]

0 голосов
/ 09 декабря 2011

Это зависит от вашего определения «чистый».В моем случае я определяю clean как: я могу реализовать желаемое поведение очевидным, эффективным способом.

Построение программного обеспечения ООП - это не упражнение по моделированию данных.Я бы предложил немного отступить.Что каждый из этих объектов на самом деле делает ?Какие методы вы собираетесь реализовать?

То, что «парни в большом количестве» не означает, что объект партии нуждается в наборе парней;он нужен только в том случае, если есть много операций, которые влияют на всех парней в нем.И даже тогда, для этого не обязательно нужна коллекция парней - , нужен способ привлечь парней в партию .Это может быть внутренне сохраненная коллекция, но это также может быть простой метод, который вызывает мир, чтобы найти парней, соответствующих критериям.Реализация этого поиска должна быть прозрачной для всех.

С точки зрения ваших вопросов кажется, что вы думаете об этом с точки зрения "как генерировать отчеты".Сделайте шаг назад и подумайте о поведении, которое вы пытаетесь реализовать в первую очередь.

Еще одна вещь, которую я считаю чрезвычайно ценной, - это различать сущности и ценности.Сущности - это объекты, для которых важна личность. У вас может быть два парня, которых зовут «Крис», но это два разных объекта, которые остаются разными, несмотря на то, что имеют один и тот же «ключ».С другой стороны, ценности действуют как целые числа.Из приведенного выше списка позиция звучит очень похоже на значение - позиция (0,0) - это позиция (0,0) независимо от того, в каком фрагменте памяти (идентичности) хранятся эти биты. Различие немного влияет на то, как высравнить и сохранить значения против сущностей.Например, ваши объекты (сущности) Guy будут хранить свое Положение как простую переменную-член.

Я нашел отличную справку о том, как думать о таких вещах, в книге Эрика Эвана «Управление через домен».Он сосредоточен на бизнес-системах, но обсуждения очень ценны для того, что вы думаете о построении ОО-систем в целом.

0 голосов
/ 09 декабря 2011

Я бы сказал, что нет 'истинный' ответ существует на ваш основной вопрос - лучший способ управления коллекциями сущностей, которые связаны несколькими способами. Это действительно зависит от типа приложения (симуляция) - вот некоторые мысли:

Важно ли время выполнения?

Если это так, то на самом деле нет анализа , каким образом ваш симулятор будет перебирать (запрашивать) объекты из пула: наметить базовый цикл симуляции и проверить, какой события потребуются для итерации по типу сущностей модели (я полагаю, вы разрабатываете моделирование дискретных событий?). Затем вы должны организовать структуры данных таким образом, чтобы оптимизировать наиболее частые / трудоемкие события (в отличие от «произвольного установления соединений»). Кроме того, вы можете использовать специальные структуры данных (такие как деревья k-d ) для организации объектов со свойствами, которые вам необходимо часто запрашивать (например, данные о положении). Для некоторых типичных проблем, например обнаружение столкновений, также существует множество подходов для их эффективного решения (поэтому ищите подходящие библиотеки / фреймворки, например, для мультиагентное моделирование ).

Насколько гибким вы хотите это сделать?

Если вы действительно хотите сделать его сверхгибким и на самом деле не хотите выбирать иерархию объектов модели, почему бы просто не использовать базу данных в памяти ? Как вы уже сказали, базы данных легко применимы к вашей проблеме (и вы можете легко сохранить состояние модели, что также может быть полезно).

Насколько чисто достаточно чисто?

Если вы хотите быть абсолютно уверены в том, что остальная часть вашего симулятора не зависит от выбора дизайна, который вы делаете в отношении представления вашей модели, скройте его за интерфейсом (скажем, ModelWorld) , который определяет методы для всех типов запросов, которые ваш симулятор может вызывать (это ортогонально второй точке и может помочь с первой точкой, то есть выяснить, какой тип доступа демонстрирует ваш симулятор). Это позволяет вам легко изменять реализации , не затрагивая другие части кода симулятора.

...