C++: непонятная проблема

Тема в разделе "WASM.ZEN", создана пользователем varnie, 18 ноя 2006.

  1. varnie

    varnie New Member

    Публикаций:
    0
    Регистрация:
    2 янв 2005
    Сообщения:
    1.785
    здравствуйте.

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


    есть один абстр. класс baseBot.

    Код (Text):
    1. //baseBot.h
    2.  
    3. namespace irr
    4. {
    5.    class baseGame;  
    6.  
    7.  /*
    8.     тут компилер ругается:
    9.     botPlayer.h:
    10.      invalid use of undefined type `struct irr::baseGame'          
    11.  */  
    12.  
    13.    class baseBot
    14.    {
    15.       public:
    16.  
    17.        baseBot( baseGame *pOwner = NULL ) : _pOwnerGame(pOwner) {}    
    18.       //etc
    19.  
    20.  
    21.  
    22.       protected:
    23.  
    24.        baseGame *_pOwnerGame;
    25.    };
    26. }
    где класс baseGame выглядит так:

    Код (Text):
    1. //baseGame.h
    2.  
    3. // include botPlayer class
    4. #include "botPlayer.h"
    5. // include botMonster class
    6. #include "botMonster.h"
    7.  
    8. namespace irr
    9. {
    10.    class baseBot;
    11.  
    12.    class baseGame
    13.    {      
    14.      
    15.       public:
    16.  
    17.        void someMethod();
    18.        int  getI() const { return i; }
    19.        //etc
    20.  
    21.  
    22.       private
    23.        botPlayer *_player;
    24.        int        _i;
    25.    };
    26. }
    27.  
    28. void baseGame::someMethod()
    29. {
    30.    _player = new botPlayer( this );
    31.    
    32.    //...
    33. }
    далее, из baseBot-a выведен botPlayer:

    Код (Text):
    1. //botPlayer.h
    2.  
    3. #include "baseBot.h"
    4.  
    5. namespace irr
    6. {
    7.    
    8.    class botPlayer : public baseBot
    9.    {
    10.       public:
    11.  
    12.       botPlayer(baseGame *pOwner);
    13.       //etc
    14.  
    15.    };
    16. }
    17.  
    18. botPlayer::botPlayer(baseGame *pOwner)
    19. {
    20.  
    21.  /*
    22.      тут компилер ругается:
    23.      botPlayer.h:
    24.       invalid use of undefined type `struct irr::baseGame'
    25.  */    
    26.  
    27.   //обращаемся через pOwner к методам класса baseGame и делаем нек. действия
    28.   int Value = pOwner->getI();
    29.  
    30. }
    т.е. кто не понял, смысл таков: есть абстр. класс baseBot, кот-й содержит указатель на главный класс baseGame, кот-й всем рулит (в частности, и этим baseBot-ом). далее, из baseBot выведен класс botPlayer.
    конкретные объекты класса botPlayer создаются в главном классе baseGame, и посему, чтобы из botPlayer-а (да и вообще, всех baseBot-ов) можно было иметь связь с "внешним миром", им в конструкторе из метода baseGame, где они создаются, передается указатель на этот baseGame.
    т.е. мне хочется сделать взаимопроникаемую систему, где baseGame будет содержать все baseBot-ы (и его потомков), и будет рулить ими, а baseBot-ы вместе с потомками будут иметь возможность "добираться" до методов baseGame-а, и всяких его "настроек".

    можете пояснить, как мне пофиксить эти ошибки?
    мне непонятно, почему в botPlayer::botPlayer(baseGame *pOwner) компилер "видит" класс baseGame, а далее в теле метода уже не видит.
     
  2. Proteus

    Proteus Member

    Публикаций:
    0
    Регистрация:
    19 июн 2004
    Сообщения:
    344
    Адрес:
    Russia
    Ты пример как-нибудь упростил. Ведь зашибёшься разбираться. На беглый вгляд всё правильно.
     
  3. Black_mirror

    Black_mirror Active Member

    Публикаций:
    0
    Регистрация:
    14 окт 2002
    Сообщения:
    1.035
    varnie
    Ругается компилятор скорее всего на то, что ты в botPlayer.h пытаешься вызывать методы baseGame, который еще не определён, определён только указатель на него. Вынеси реализацию методов в cpp-файл и попробуй включить туда baseGame.h.

    На мой взгяд позволять ботам вызывать все методы baseGame не есть хорошо, раз есть метод который создаёт бота, значит должен быть метод который его удаляет, и если бот вдруг надумает его вызвать, программа скорее всего упадёт.
    Думаю лучше создать интерфейс IForBots с методами которые нужны ботам и наследовать baseGame от него, а ботам передавать указатель на IForBots.
     
  4. fr0b-p

    fr0b-p New Member

    Публикаций:
    0
    Регистрация:
    1 окт 2006
    Сообщения:
    118
    объявление и реализацию класса botPlayer следует помещать в одном namespace
     
  5. varnie

    varnie New Member

    Публикаций:
    0
    Регистрация:
    2 янв 2005
    Сообщения:
    1.785
    fr0b-p,
    так у меня класс botPlayer и его реализация и так в одном нэймспейсе. все это у меня в botPlayer.h идет.
    black mirror,
    поясни еще раз пожалуйста - что и куда включить, а то я не оч понял.
     
  6. fr0b-p

    fr0b-p New Member

    Публикаций:
    0
    Регистрация:
    1 окт 2006
    Сообщения:
    118
    namespace irr
    {


    class botPlayer : public baseBot
    {
    public:

    botPlayer(baseGame *pOwner);
    //etc

    };
    }

    botPlayer::botPlayer(baseGame *pOwner)
    {
     
  7. varnie

    varnie New Member

    Публикаций:
    0
    Регистрация:
    2 янв 2005
    Сообщения:
    1.785
    так у меня же это именно так и сделано. нэймспейс irr у class basePlayer-a этот.
     
  8. Black_mirror

    Black_mirror Active Member

    Публикаций:
    0
    Регистрация:
    14 окт 2002
    Сообщения:
    1.035
    varnie
    h-файлы для ботов делаешь так:
    Код (Text):
    1. #ifndef _botXX_h_
    2. #define _botXX_h_
    3.  
    4. //сюда можно включить что угодно за исключением baseGame.h
    5.  
    6. class gameGame;
    7.  
    8. class botXX
    9. {
    10. //здесь используешь только указатели или ссылки на baseGame
    11. baseGame *g;
    12. someMethod(...,baseGame*a,...);
    13. };
    14.  
    15. #endif
    cpp-файлы для ботов:
    Код (Text):
    1. #include "botXX.h"
    2. #include "baseGame.h"
    3. //сюда включаются остальные файлы
    4.  
    5. botXX::someMethod(...)
    6. {
    7. //здесь можно вызывать методы baseGame
    8. g->someMethod(...);
    9. }
    c baseGame желательно поступить так же, то есть в определении класса используем только указатели на ботов, а в реализации уже вызываем их методы.
     
  9. fr0b-p

    fr0b-p New Member

    Публикаций:
    0
    Регистрация:
    1 окт 2006
    Сообщения:
    118
    varnie - так сейчас сделано не правильно !
    объявление классов botPlayer и baseGame сделаны в namespace irr
    a
    botPlayer::botPlayer(baseGame *pOwner)
    в глобальном неймспейсе !
    после исправления этого и пары других опечаток все скомпилицо
     
  10. varnie

    varnie New Member

    Публикаций:
    0
    Регистрация:
    2 янв 2005
    Сообщения:
    1.785
    сделал, как сказал Black_Mirror, плюс еще я глянул вот здесь описание этой проблемы.

    заработало!
     
  11. fr0b-p

    fr0b-p New Member

    Публикаций:
    0
    Регистрация:
    1 окт 2006
    Сообщения:
    118
    покажи теперь компилируемый код и мы все увидим что неймспейс один :)
     
  12. varnie

    varnie New Member

    Публикаций:
    0
    Регистрация:
    2 янв 2005
    Сообщения:
    1.785
    да, все было так как вы и сказали. спасибо за помощь! и пардон что так поздно на связь вышел. я тут пропадал просто кое-где.
    тема закрыта.