2013-12-13 2 views
0

В моей игре TicTacToe у меня проблемы с виртуальными функциями. Следующий код генерирует ошибку в Dev C++: «class std :: auto_ptr» не имеет имени с именем «makeAMove».Как получить доступ к объекту, на который указывает std :: auto_ptr

Согласно ошибке, проблема имеет какое-то отношение к функции makeAMove, но я не могу посмотрите, что случилось. Кроме того, я должен упомянуть, что я использую устаревшую функцию auto_ptr вместо unique_ptr, потому что, по-видимому, помощь преподавателя, сортирующая мой код, не имеет компилятора, совместимого с C++ 11.

Прямо сейчас и playGame, и makeAMove функции don не делайте ничего, но я хочу выяснить, что вызывает ошибку, прежде чем продолжить.

Благодарим за любые предложения.

Вот соответствующий код:

Game.h (действует как контроллер для игры)

#include "Player.h" 
#include "AIPlayer.h" 
#include "HumanPlayer.h" 
#include <memory> 

class Game 
{ 
    public: 
     Game(unsigned int players) 
     { 
      if (players == 1) 
      { 
       player1.reset (new HumanPlayer()); 
       player2.reset (new AIPlayer()); 
      } 
      else 
      { 
       player1.reset (new HumanPlayer()); 
       player2.reset (new HumanPlayer()); 
      } 
     } 

     void playGame() 
     { 
      player1.makeAMove(); 
     } 

    private: 
     std::auto_ptr<Player> player1; // pointer to a Player object (C++11 has more secure unique_ptr) 
     std::auto_ptr<Player> player2; // pointer to a Player object 
}; 

Player.h (базовый класс для обоих HumanPlayer.h и AIPlayer.h)

class Player 
{ 
    public: 
     virtual void makeAMove() = 0; // will accept pointer to board object as param 
}; 

HumanPlayer.h

class HumanPlayer : public Player 
{ 
    public: 
     virtual void makeAMove() 
     { 
      // do some work 
     } 
}; 

AIPlayer.h

#pragma once // include guard 
#include "Player.h" 

class AIPlayer : public Player 
{ 
    public: 
     virtual void makeAMove() 
     { 
      // do some work 
     } 
}; 

main.cpp

#include <iostream> 
#include "Game.h" 

int main() 
{ 
    Game myGame(1); 
    myGame.playGame(); 

    return 0; 
} 

ответ

1

Я думаю, что ваше намерение состоит в том, чтобы сделать:

player1.get()->makeAMove(); 

Вы должны вызвать makeAMove на объект игрока, принадлежащего auto_ptr, а не на auto_ptr сам. Хотя вы можете разыменовать auto_ptr так же, как и обычный указатель (как указывали другие) благодаря перегруженным операторам.

+3

'player1-> makeAMove();' достаточно, не нужно явно вызывать 'get()' в этом случае. –

5

Имейте в виду, что auto_ptr действует точно так же, как указатель, поэтому вам нужно разыгрывать (либо с operator*, либо operator->).

3

Умные указательные обертки ведут себя точно так же, как указатели. То есть, если вы хотите использовать функции указателя (в данном случае makeAMove), вам необходимо разыменованием ему:

player1->makeAMove(); 

В основном то, что происходит здесь, является operator-> вернет Player* позволяет вызвать соответствующую функцию-член от Player. используя operator., вы получите доступ к функциям члена auto_ptr (что не то, что вы хотите в этот момент вашего кода).

+0

Должен ли я каждый раз вызывать функцию таким образом. – navig8tr

+0

Вы также можете вызвать его через '(* player1) .makeAMove()', если хотите, но да. В синтаксисе он идентичен вызову функции через необработанный указатель. –

+0

Спасибо большое объяснение! – navig8tr