Линкер не может найти символы для поля stati c, доступного в виртуальном классе c ++ - PullRequest
2 голосов
/ 17 февраля 2020

Я улучшал свой код посетителя код в c ++ , который изначально выглядел как код, приведенный ниже, чтобы избавиться от ненужной части, в которой посетитель должен передать себя accept void.

Я пришел к простому решению, которое «превращает» параметр в static field, чтобы я мог инициализировать поле прямо перед тем, как использовать accept.

Прости мне, но мне нужно сделать это, даже если это будет очень некрасиво.

Старый код:

class A_Child;
class B_Child;

class Father {
    public:
    virtual ~Father() = default;
    class Visitor {
        public:
        virtual void visitChildA(A_Child * child) = 0;
        virtual void visitChildB(B_Child * child) = 0;
    };
    virtual void accept(Visitor * visitor) = 0;
};

class A_Child: public Father {
    public: /* A Child Stuff */
    void accept(Visitor * visitor) override;
};

class B_Child: public Father {
    public: /* B Child Stuff */
    void accept(Visitor * visitor) override;
};

A_Child::accept(Visitor * visitor) { visitor -> visitChildA(this); }
B_Child::accept(Visitor * visitor) { visitor -> visitChildB(this); }

Новый код:

class Father {
    public:
    virtual ~Father() = default;
    class Visitor {
        public:
        virtual void visitChildA(A_Child * child) = 0;
        virtual void visitChildB(B_Child * child) = 0;
    };
    static Visitor * visitor;
    virtual void accept() = 0;
};

// Outside, (assuming NewVisitor: public Father::Visitor):

void NewVisitor::DoStuff(Father * child) {
    Father::visitor = this;
    child -> accept();
}

Жалобы компоновщика:

Мой компоновщик недоволен этим и выдает мне следующий вывод:

Undefined symbols for architecture x86_64:
  "Father::visitor", referenced from:
      Child_A::accept() in Father.o
      Child_B::accept() in Father.o
ld: symbol(s) not found for architecture x86_64

Кто-нибудь знает почему это происходит? Я нарушаю какое-то загадочное OOP правило?

1 Ответ

2 голосов
/ 17 февраля 2020

Вы должны определить переменную some где. Строка типа

Visitor* Father::visitor = nullptr;

в вашем файле. cpp в глобальной области видимости должна подойти.

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