Фабричный метод и циклическая зависимость - PullRequest
0 голосов
/ 06 мая 2010

Редактировать: Спасибо, ребята, теперь я вижу свою ошибку.

Если я не ошибаюсь, из-за своей природы в фабричном методе существует циклическая зависимость:

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

Практически я реализовал фабрику, у меня проблема выше, даже я добавил

#ifndef MYCLASS_H
#define MYCLASS_H
#endif

Я все еще получаю

Compiler Error C2504 'class' : base class undefined

И эта ошибка вызывает ошибку при удалении включения подкласса из заголовка базового класса.

Ответы [ 4 ]

4 голосов
/ 06 мая 2010

Фабрика не должна быть базовым классом продукции.

3 голосов
/ 06 мая 2010

Решение 1. Не включайте # заголовки производного класса в заголовок базового класса, только в базовый класс cpp. Объявление метода фабрики не должно использовать тип возвращаемых конкретных классов, только базовый тип.

Решение 2: используйте отдельный класс фабрики (или метод фабрики в отдельном классе) для создания ваших объектов. Тогда циклическая зависимость полностью исключается. Это предпочтительный способ.

1 голос
/ 06 мая 2010

Базовые классы никогда не должны знать о производных классах.

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

В сообщении об ошибке, которое вы получаете выше, производные классы всегда должны знать полную реализацию базового класса. При разработке базовые классы никогда не должны знать ничего о производных классах.

0 голосов
/ 06 мая 2010
struct Base {
    Base * Create(int param);
};

struct Derived0 : public Base {
};

struct Derived1 : public Base {
};

Base * Base::Create(int param) {
    switch (param) {
    case 0: return new Derived0();
    case 1: return new Derived1();
}

Не следует пытаться реализовать функцию фабрики в определении базового класса. Просто объявите его там и определите после определения производных классов.

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