2011-02-03 2 views
6

Мой вопрос здесь не строго связан с языком, это скорее общая концепция программирования.Лучше иметь механизм кэширования внутри или вне класса Factory?

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

Лучше с точки зрения использования и разделения объектов создать механизмы кэширования для всех созданных экземпляров Parsers внутри Factory, то есть: во время вызова метода или вне его, когда метод уже вызван?

Заранее спасибо.

ответ

5

Возможно, вы можете определить интерфейс для своего Factory, а затем выполнить несколько реализаций - одна реализация может выполнять кэширование внутри, чтобы гарантировать, что класс Parser создается только один раз. Другая реализация не может выполнять кэширование и просто предоставлять новые объекты Parser всякий раз, когда что-то запрашивает их.

В любом случае, я предлагаю вам попытаться сохранить эту логику в своих реализациях Factory, а остальные приложения будут работать с интерфейсом Factory. Таким образом, если позже вы решите, что не хотите кэшировать что-либо или что вам нужно изменить способ создания объекта Parser, у вас будет только одна точка создания объекта - внутри Factory. Это позволяет легко изменить способ создания объектов Parser, не изменяя каждую часть приложения, которая хочет новый Parser.

Еще раз - если вы создаете механизмы кэширования для работы за пределами Factory, тогда эти механизмы будут на всем протяжении вашего кода, так как вы должны использовать их, когда хотите получить новый Parser. Если позже вы решите изменить механизм кеширования, вам придется прикоснуться к большому количеству кода, но если вы выполните кэширование внутри Factory, вам нужно будет только изменить реализацию Factory.

+0

См. Также [Принцип единой ответственности] (http://en.wikipedia.org/wiki/Single_responsibility_principle) –

+0

@Tom Brito: Я понимаю принцип, но вам нужно объяснить, как это относится к этой ситуации. –

+0

На самом деле, я отправил его всем, кто видит ваш ответ, а не специально для вас. Принцип относится к ситуации, поскольку он спрашивает, должен ли у его класса быть или нет еще одна ответственность, чем он уже имеет. Следуя этому принципу, ответ отрицательный, механизм кэширования должен быть размещен снаружи, в другом классе. Конечно, это будет зависеть от его проекта, но если он хочет получить образец, это может быть хорошим. –

0

Звучит для меня как то, что вам нужно использовать, это Singleton Pattern.

+0

Singleton - это единственный экземпляр объекта, я должен управлять отдельными экземплярами многих объектов в кешированном виде ... даже используя Singleton для парсеров. Мне все еще нужно кэширование. – OverLex

+0

@ LEX Используйте шаблон singleton для объектов парсера для их кэширования, и Factory возвращает экземпляр singleton того, что требуется изготовителю. – Becuzz

+0

@Becuzz Почему бы просто не обратиться непосредственно к Синглтону вместо того, чтобы проходить через Фабрику? – Caelum

0

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

Если у вас есть несколько классов, подобных этому, вы можете использовать шаблон прокси. Класс Proxy будет реализовывать тот же интерфейс, что и реализация Factory, и делегировать его на завод только в том случае, если объект, который будет возвращен с Factory, еще не находится в кеше Proxy.

Использование динамического прокси расширит этот подход и позволит реализовать кэширование везде, где вы хотите, с очень небольшим дополнительным расширением библиотеки (но ценой повышенной сложности).

2

Я не понимаю проблему: клиенты фабричного класса не заботятся о том, кэшируются ли объекты, которые они получают, или нет. Поэтому логика кэширования должна быть принадлежит к заводу.

Кроме того, когда вы реализуете это, вы сначала реализуете завод без кеширования, чтобы что-то быстро работало (Простейшая вещь, которая могла бы работать). Затем вы реализуете кеширование.Обратите внимание, что делать что-либо еще в случае преждевременной оптимизации. Если клиентские классы должны были знать, будут ли кешированные объекты или нет, ваш процесс разработки быстро сгорит.

Как вы реализуете это зависит от вас. Мне нравится писать один раз в общий класс кеширования и повторно использовать его в подобных ситуациях, но вы могли бы подумать о других механизмах. Кроме того, я не делаю java, и поэтому я не могу заявить о том, что лучше делать здесь.

(PS: Я вижу много проблем с шаблоном проектирования в ответах на этот вопрос. Разве это распространено среди людей java, чтобы всегда думать с точки зрения шаблонов? Нет никаких синглов для проектирования, без прокси-классов, чтобы писать здесь, только простые рассуждения о том, какой интерфейс не может измениться).

+0

Я уже сделал, как вы сказали, первая реализация была без кэширования, я сейчас представляю кэширование как форму оптимизации и задаюсь вопросом, какой подход должен быть лучшим. Да, мышление в моделях распространено в мире Java, это группа из четырех, которая сформировала нас всех, к счастью или нет :) – OverLex

+0

@ Lex: для меня шаблоны проектирования всегда были в основном тривиальными вещами, которые вы могли бы придумать самостоятельно или обходные пути для поддержки отсутствующих языков. Нарушение шаблонов превращает вас * программиста в программу. Но они могут помочь вам придумать хорошую практику проектирования, если вы хорошо поймете, когда они применяются, а главное, когда они этого не сделают. У меня такое ощущение, что «java школы» (во Франции, самые дерзкие школы программирования учат Java, следовательно, мои необоснованные предрассудки о java) стараются не думать о себе. –

Смежные вопросы