2017-01-15 9 views
1

Редактировать: Добавлен код из заголовка файла.Inhertitance + использование объекта (this) в качестве аргумента

Сейчас я работаю над каким-то симуляцией, и возникли некоторые проблемы. У меня есть несколько классов, как этот ниже:

#ifndef CARTYLERIA_H 
#define CARTYLERIA_H 
#include "cjednostka.h" 
#include "cnieruchome.h" 
#include "battlewindow.h" 

class BattleWindow; 

class CArtyleria : public CJednostka, public CNieRuchome <------ error line 
{ 
public: 
    CArtyleria(); 
    void rysuj(BattleWindow *okno); 
}; 

#endif // CARTYLERIA_H 

И когда я пытаюсь скомпилировать есть ошибка в отмеченной линии:

ожидается класс имя, прежде чем «» Маркер

Все работает правильно, пока я не добавлю указатель на объект BattleWindow.

Это хорошая практика, чтобы вызвать метод CArtyleria с

это

в BattleWindow объект класса?

Cjednostka.h:

#include "battlewindow.h" 

    class CJednostka 
    { 
    public: 
     CJednostka(); 
     virtual void rysuj (BattleWindow *okno) =0; 
} 

CNieRuchome.h:

class CNieRuchome 
{ 
public: 
    CNieRuchome(); 
protected: 
    int PozycjaX; 
    int PozycjaY; 
}; 

И battlewindow.h:

#include <coddzial.h> 
#include "main.h" 
#include "ctimer.h" 
#include "cpotyczka.h" 
#include "cjednostka.h" 

namespace Ui { 
class BattleWindow; 
} 
class CPotyczka; 
class BattleWindow : public QMainWindow 
{ 
    Q_OBJECT 

public: 
    CPotyczka *potyczka; 
    void tworz_oddzial(); 
    explicit BattleWindow(QWidget *parent = 0); 
    ~BattleWindow(); 
    std::vector <QGraphicsPixmapItem*> items_vector; 
    void dodaj_jednostki(std::vector<QString> jednostki, QString frakcja); 
    void rysuj_jednostke(QString jednostka, QString frakcja, int x, int y); 

private slots: 

    void on_now(); 

private: 

    QGraphicsScene *scene; 
    Ui::BattleWindow *ui; 
    CTimer *timer; 


    void rysuj_jednostki(QString frakcja); 
    void rysuj_plansze(); 
    void rysuj_flagi(); 
    void usun_jednostke (QGraphicsPixmapItem *item); 
    std::list<CJednostka*> jednostki_do_narysowania; 
}; 

И то, что я хочу сделать, это:

вызов метода для объектов в S Список TL std::list<CJednostka*> jednostki_do_narysowania;

Сейчас она реализуется, как показано ниже:

for(std::list <CJednostka*>::iterator it=jednostki_do_narysowania.begin();it!=jednostki_do_narysowania.end();++it){ 

     (*it)->rysuj(this); 
+3

Итак, вы добавили аргумент 'okno', а затем вы получили ошибку для строки, которая определяет базовые классы? Это звучит не так. Как бы то ни было, вы не предоставили достаточно кода. Мы не знаем, что в ваших трех файлах '* .h'. –

+0

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

+0

Если вы перешли декларативный боевой бросок, вы можете удалить оператор include. что поможет. – Soeren

ответ

0

Есть несколько проблем с этим кодом.

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

Также у вас есть круговая зависимость между cjednostka.h и battlewindow.h.

Поскольку cjednostka.h имеет только интерфейс класса удаления включают и добавить опережающее объявление для class BattleWindow, как вы делали в cartyleria.h

Следующая проблема в том, что вы создаете чистый виртуальный интерфейс для CJednostka, но это не делает имеют виртуальный деструктор. Это очень плохо и в конечном итоге приведет к неправильному уничтожению объекта с помощью базового указателя.

Попробуйте это в cjednostka.h

#ifndef CJEDNOSTKA_H 
#define CJEDNOSTKA_H 
class CJednostka 
{ 
public: 
    CJednostka(); 
    virtual ~CJednostka() = default; 
    virtual void rysuj (BattleWindow *okno) =0; 
}; 
#endif 

Также я рекомендую использовать либо охранников заголовков во всех файлах заголовков или #pragma один раз. Просто придерживайтесь одного варианта и делайте это в каждом заголовке.

Другая проблема с заголовками, что в одном из них вы включаете свой собственный заголовок, как #include <coddzial.h> вместо #include "coodzial.h" это может привести к проблемам, как есть разница в <> против «». Первый из них искал библиотеку Include path, последний ищет файл относительно ваших файлов проекта, и это, скорее всего, то, что вы хотите.

Наконец, предложение в 90% векторов сценариев превосходит списки, и у меня есть сильное чувство, что вам не нужен список. Я рекомендую снова проверить различия между ними.

+0

Ребята, я пытаюсь исправить указанные проблемы, но есть несколько дополнительных вопросов. Когда я добавляю объявление класса в родительский класс: CJednostka необходимо сделать это снова в унаследованных классах, есть ли у них знания и доступ к нему? – BBq

+0

@BBq читает книгу или учебник по классам C++ и Inheritance. Я не уверен, что вы подразумеваете под словом add add в родительском классе. –