Единого ответа не существует - дизайн состоит в том, чтобы совмещать приоритеты, компромиссы и компромиссы, чтобы получить что-то, что хорошо работает в вашей ситуации. Я кратко расскажу об относительных достоинствах и недостатках использования функторов, методов доступа и полной инкапсуляции.
функторы
Использование функторов может быть удобным и позволяет избежать итерации. Это также позволяет вам четко отделить то, что вы выполняете для каждого элемента в списке, от момента его выполнения. С циклом for-each эти два чаще всего связаны вместе. Функторы не работают, если вам нужно выполнить операцию над несколькими списками, либо из одного и того же объекта, либо из нескольких объектов, либо если вам нужны только несколько элементов списка. Использование функторов ограничивает порядок выполнения - элементы должны использоваться в порядке, повторяемом поставщиком. Функтор не имеет контроля. Это может быть благословением, а также проклятием.
В качестве примера Person, предпочтений планирования и планировщика, планировщик может предоставить внешний итератор для возможных времен расписания:
schedules = scheduler.schedules(person.getSchedulePreferred())
getSchedulePreferred () возвращает предикат, который выбирает расписания из всех доступных, которые предпочитает данный человек.
Итерации по всем графикам могут быть не самым эффективным способом реализации этого. Скажем, если человек хочет только графики в июне, то все графики на оставшуюся часть года будут расточительно повторяться.
Accessors
Создание списков, доступных через gtters, может быть полезно при реализации функциональности, не свойственной классу. Например, с учетом двух Орденов найдите общие для них предметы. Это просто реализовать, если списки предоставляются как получатели для внешнего обхода, и очень просто, если списки предоставляются в некотором известном порядке (например, если у Order есть метод getSortedItems()
.) Сложность здесь заключается в управлении изменчивостью списка, хотя многие языки имеют прямую поддержку для отключения мутации (например, const в C ++) или обертывания списка в неизменяемую оболочку.
Например, человек может предоставить список предпочтений расписания, которые затем будут использованы непосредственно планировщиком. Планировщик имеет возможность быть «умным» в отношении того, как применяются предпочтения, например, он может создать запрос к базе данных для получения соответствующих расписаний на основе предпочтений сотрудников.
Encpasulation
Третий вариант - вопрос, требуется ли внешний доступ. Это один из признаков модели анемичной области , что все объекты имеют свойства и не имеют поведения. Но не пытайтесь поместить поведение в объект домена только для того, чтобы избежать этого анти-паттерна - поведение должно быть естественной частью ответственности этого объекта.
Я не думаю, что это применимо здесь - предпочтения человека, планировщика и планирования четко выполняют разные роли и имеют четкие обязанности. Добавление метода к одному объекту, который пытается вычислить данные из другого, был бы ненужной тесной связью.
Краткое описание
В этом конкретном случае я предпочитаю геттер, поскольку он позволяет планировщику лучше контролировать использование предпочтений расписания, а не «принудительно их» через функтор.