抱歉,我在这件事上缺乏经验,如果这是一个简单的答案,但我正在为一项作业编写一个 C++ 程序,并且我一生都找不到解决方案。
我创建了一个名为 Door 的类,它拥有一个本地变量,用于存储它所连接的房间。此外,每扇门都通过另一个局部变量相互连接。记录每扇门所连接的门的局部变量是一个指针(赋值的要求)。
门类通过取消引用指针(通过 * 运算符)将其连接到的门传回。
另一个类 Room,在四个方向(北、东等)后面的变量名称中存储四个门,并由一个简单的整数标识,该整数可以通过函数传递以接收指向房间对象的共享指针。
我遇到的问题是在我的类中,该类负责创建房间并用门填充它们,然后将门彼此连接,程序能够设置 Door 类的局部变量,但是,一旦刚刚设置了变量的门对象被引用回它似乎设置了错误的变量。
在下面的示例中,正在创建的房间的整数是 1 和 2。
这不是完整的代码,只是相关信息的片段
class Door{
private:
Door *_connectedDoor;
int _connectedRoom;
bool _isEntrance;
bool _isExit;
};
void Door::connectDoor(Door connectedDoor){
if( _isExit == true || _isEntrance == true)
{
std::cout << "Cannot connect, is an entrance / exit";
}
else
{
_connectedDoor = &connectedDoor;
}
};
Door Door::getConnectedDoor(){
return *_connectedDoor;
}
int Door::getRoom(){
std::cout << std::endl << "*** passing connected room:" << _connectedRoom << " ***" << std::endl;
return _connectedRoom;
};
void Door::setRoom(int room){
std::cout << std::endl << "*** setting connected room:" << room << " ***" << std::endl;
_connectedRoom = room;
};
class Room{
private:
int _id;
std::string _description;
Door _northDoor;
};
void Room::setNorth(Door north){
_isDoorNorth = true;
_northDoor = north;
std::cout << std::endl << "*** configuring doors room internally to:" << _id << " ***" << std::endl;
north.setRoom(_id);
};
类游戏
void Game::connectRooms(int room1, int room2, std::string startingDirection)
{
std::cout << std::endl << "*** connecting rooms ***" << std::endl;
std::shared_ptr<dungeon::Room> startingRoom = _currentDungeon.retrieveRoom(room1);
std::shared_ptr<dungeon::Room> endingRoom = _currentDungeon.retrieveRoom(room2);
dungeon::Door startingRoomDoor = *new dungeon::Door();
dungeon::Door endingRoomDoor = *new dungeon::Door();
std::cout << std::endl << "*** configuring room:" << startingRoom->id() << " ***" << std::endl;
std::cout << std::endl << "*** configuring room:" << endingRoom->id() << " ***" << std::endl;
startingRoom->setNorth(startingRoomDoor);
endingRoom->setSouth(endingRoomDoor);
std::cout << std::endl << "*** configuring doors room:" << startingRoomDoor.getRoom() << " ***" << std::endl;
std::cout << std::endl << "*** configuring doors room:" << endingRoomDoor.getRoom() << " ***" << std::endl;
startingRoomDoor.connectDoor(endingRoomDoor);
endingRoomDoor.connectDoor(startingRoomDoor);
};
输出:
*** connecting rooms ***
*** configuring room:1 ***
*** configuring room:2 ***
*** configuring doors room internally to:1 ***
*** setting connected room:1 ***
*** configuring doors room internally to:2 ***
*** setting connected room:2 ***
*** configuring doors room:
*** passing connected room:1835344 ***
1835344 ***
*** configuring doors room:
*** passing connected room:1835344 ***
1835344 ***
预期:
*** configuring doors room:
*** passing connected room:1 ***
1 ***
*** configuring doors room:
*** passing connected room:2 ***
2 ***
最佳答案
首先:很高兴看到您使用 std::shared_ptr
!我认为你的问题是对象的复制。由于我不知道这是否只是一个拼写错误或其他原因,我会更详细地解释一下。让我们看一下您的一些代码:
dungeon::Door runningRoomDoor = *new dungeon::Door();
这将执行以下操作:
- 使用
new
运算符创建dungeon::Door
的新实例。这将返回一个指向新实例的指针。 - 使用
*
取消引用该指针。 - 使用新实例初始化
startingRoomDoor
,从而调用复制构造函数并复制新实例。 - 指向新实例的指针超出范围,导致内存泄漏。
您可以使用 std::shared_ptr
修复此问题,就像使用 startingRoom
和 endingRoom
一样。或者,您可以只编写 dungeon::Door runningRoomDoor;
并拥有 dungeon::Door
的初始化实例。在这种情况下,构造函数会被自动调用。
接下来是您的房间功能:
void Room::setNorth(Door north){
_isDoorNorth = true;
_northDoor = north;
std::cout << std::endl << "*** configuring doors room internally to:" << _id << " ***" << std::endl;
north.setRoom(_id);
}
在这里,您可以按值传递北
。这意味着,您传递给此函数的值实际上会被复制,并且在函数内您仅修改 Room
的拷贝。在函数结束时,north
被销毁,因为它的作用域到此结束。如果您像这样通过引用传递,则可以解决此问题: void Room::setNorth(Door &north)
现在,您实际上修改了传递给函数的值而不是拷贝。
但请注意! _northDoor = Northern;
行仍将复制 north
。即使 north
是通过引用传递的。也许您只想存储一个指针而不是整个实例?您还可以使用 std::shared_ptr
来实现此目的。
关于c++ - 我创建的类似乎错误地设置了它的局部变量,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58247725/