Обработка взрывов бетонных классов на абстрактной фабрике - PullRequest
1 голос
/ 21 августа 2009

Как описано в мотивации использования Abstract Factory , мне нужен интерфейс, который я хочу быть очень гибким, то есть он должен иметь ряд возможных вариантов поведения. Итак, следуя шаблону проектирования AF, я определяю абстрактный класс с интерфейсными функциями следующим образом:

class WidgetFactory{
...
public:
       CreateScrollBar();
       CreateButton();
...
};

и затем я определяю конкретный подкласс WidgetFactory для каждого поведения, причем каждый подкласс реализует интерфейс для определенного поведения.

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

Ответы [ 5 ]

2 голосов
/ 21 августа 2009

Иметь отдельную фабрику для каждого из независимых интерфейсов, а затем мастер-фабрику, где можно зарегистрировать все второстепенные фабрики.

class ScrollBarFactory
{
    public:
        CreateScrollBar();
};
class ButtonFactory
{
    public:
        CreateButton();
};


// I just used templates as a quick example
// This can be doen in many ways. I hope you get the idea.
template<typename SF,typename BF>
class WidgetFactory
{
    public:
        CreateScrollBar()   {scrollbarFactory.CreateScrollBar();}
        CreateButton()      {buttonFactory.CreateButton();}
    private:
        SF    scrollbarFactory;
        BF    buttonFactory;
};
1 голос
/ 21 августа 2009

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

0 голосов
/ 23 августа 2009

На самом деле эта проблема обсуждается в книге GoF. Решением является использование паттерна Bridge. Но я не уверен, что у вас есть такая же проблема, как мне кажется странным, что

У меня есть 10 функций в абстрактном классе, и у каждой функции есть 4 возможных реализации. Так что получается, что я должен реализовать 4 ^ 10 подклассов, учитывающих каждое возможное поведение.

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

0 голосов
/ 21 августа 2009

Было бы возможно использовать что-то вроде шаблона команды внутри абстрактной фабрики. Вы передаете фабрике команды, которые она должна выполнить. Это составляет 1 команду на реализацию, один интерфейс и 1 фабрику, которая может выполнять все 4+ команды.

Дополнительная информация о настройке может помочь немного больше.

0 голосов
/ 21 августа 2009

Обычно мы не ожидаем, что у нас будет любая возможная комбинация функций.

Например, мы не будем смешивать Windows CreateScrollBar и Linux CreateButton.

Итак, ваши 4 разные реализации для каждого метода естественным образом группируются таким образом? Итак, у вас есть WindowsWidgetFactory и LinuxWidgetFactory - эта идея работает для вас?

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

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...