第一次在这里发帖,如果这是初学者的问题,很抱歉。我正在尝试为我正在制作的简单游戏创建一个 Snake 类,但调试器不断抛出奇怪的异常。
每次我调试程序时,它都会将我带入一个"矢量"文件,将我指向某一行并说:"读取访问冲突。当我在没有调试的情况下运行它时,它只是以消息终止:"使用 code -1073741819 退出。
几个小时以来,我一直在尝试解决这个问题,但仍然不知道问题是什么。我的代码有问题,还是问题不在那里?提前感谢!
在Snake.h中:
#include <vector>
class Snake{
private:
std::vector<sf::RectangleShape> body;
int speed;
public:
Snake();
void draw_body(sf::RenderWindow& windowRef);
void move(sf::RenderWindow& windowRef);
void set_speed(int s);
};
在Snake.cpp中:(我还没有完成Snake::move((
#include "Snake.h"
#include <SFMLGraphics.hpp>
Snake::Snake() : speed{ 10 }, body{ sf::RectangleShape { sf::Vector2f(50.f,50.f) } }{
body.at(0).setPosition(50.f, 50.f);
}
void Snake::draw_body(sf::RenderWindow& windowRef) {
for (sf::RectangleShape rect : body) {
windowRef.draw(rect);
}
}
void Snake::set_speed(int s) {
speed = s;
}
void Snake::move(sf::RenderWindow& windowRef) {
;
}
在主要.cpp:
#include <SFMLGraphics.hpp>
#include <iostream>
#include "Snake.h"
class Snake;
int main() {
sf::RenderWindow window(sf::VideoMode(800, 800), "MY window", sf::Style::Close | sf::Style::Titlebar);
Snake* snake{};
while (window.isOpen())
{
sf::Event event;
while (window.pollEvent(event))
{
}
window.clear(sf::Color::White);
snake->draw_body(window);
window.display();
}
return 0;
}
这是因为您的代码具有未定义的行为 (UB(。 它可以是巧合,它可以在没有任何症状的情况下失败,或者可能发生最奇怪的事情。
调试器通常会格外小心,添加大量控件。 幸运的是,它发现了空指针的使用。 事实上,这一行并没有你想象的那样:
Snake* snake{};
不会创建任何Snake
。snake
是指向Snake
的指针。 所以你刚刚初始化了一个指针。 您认为它的价值是什么?
这里最好的选择是摆脱指针:
Snake snake{}; // no *, so now you have a real snake object ready to use
...
snake.draw_body(window); // no -> since it's no longer a pointer
这一行:
Snake* snake{};
不初始化 Snake 类的实例,而是初始化指向实例的指针。指针是程序集级别的整数,默认情况下初始化为 0,与 C 中的NULL
和现代C++中的nullptr
相同的数值(它们在程序集级别都是相同的(。
要解决此问题,您需要使用new
在堆上分配一个 Snake 实例,并在使用它完后delete
它,或者通过删除指针在堆栈上分配实例。