Реализуйте конструктор копирования для функции стирания вектора - PullRequest
0 голосов
/ 25 декабря 2011

Основываясь на проблемах, возникших в результате предыдущих вопросов: vector :: erase с указателем , Удаление элементов вектора внутри цикла , мне все еще нужна помощь по vector.erase функция. Мне было сказано реализовать конструктор копирования, чтобы заставить функцию стирания работать с вектором, что также упоминается в другом вопросе. Важно реализовать оператор функции в моем соответствующем классе. При этом я получаю еще одну ошибку при создании конструктора копирования и долго не могу найти причину. Ошибка «Player :: Player (const Player & otherPlayer) не предоставляет инициализатор для:». Что я делаю неправильно? Учтите, что Player содержит карту членов класса, указатели и ссылку (банк является ссылкой). Достаточно ли простого присвоения для инициализации?

Что мне делать?

class Player
{
public:
Player(int,int,string, Bank&);
Player(const Player&); 
Player& operator = (const Player& rhs); 


Player::Player(const Player& otherPlayer)
{
ID = otherPlayer.ID;  
pName = otherPlayer.pName;
pMoney = otherPlayer.pMoney;
doubleIndicator = otherPlayer.doubleIndicator;
position = otherPlayer.position;
bank = otherPlayer.bank;
colBought = otherPlayer.colBought;
housesColBuilt = otherPlayer.housesColBuilt;

}

Обновление: Я получаю предупреждение в точке реализации оператора = как: «возвращение адреса локальной переменной или временной». Это вызывает реальную проблему? Если так, как я мог изменить это, чтобы преодолеть это?

Player& Player::operator=(const Player& rhs)
{
return Player(rhs);
}

Таким образом, я все еще получаю предупреждение о том, что рекурсивная функция вызовет переполнение стека:

Player& Player::operator=(const Player& rhs)
{
*this = Player(rhs);
return *this;
}

Есть подсказка?

1 Ответ

3 голосов
/ 25 декабря 2011

Вы должны инициализировать ссылки, которые являются членами класса, с инициализатором члена в конструкторе:

Player::Player(const Player& otherPlayer) : 
    bank(otherPlayer.bank)
{
    //...
}

Это необходимо, потому что в противном случае ссылка была бы неинициализированной, что недопустимо.

Обратите внимание, что присвоение bank = otherPlayer.bank; делает что-то другое: оно назначает объект, на который ссылается, а не устанавливает саму ссылку.

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

...