我是c +的新手,这个问题可能看起来很无趣,因为我只是更多的Java / Actionscript3而且我以前从未处理过与内存相关的事情。
无论如何我的问题是: 场景是一个抽象类(所以我可以从它派生并有多个场景,如MainScene等')
我想要SceneManager要做的是有一个指向选定场景的指针/参考(curSc) 然后我就像这样设置场景:setScene(& someScene)
但据我所知,要有一个指针,我还必须像这样初始化它: curSc =新场景; 但它不会让我这样做,因为Scene是一个抽象类......
class Scene {
public:
Scene(void){}
virtual ~Scene(void){}
virtual void update() = 0;
virtual void render() = 0;
};
class SceneManager {
public:
SceneManager(void);
~SceneManager(void);
void setScene(Scene *sc);
Scene* curSc;
}
到目前为止,在我看来,在这种情况下使用指针是错误的,它将无法工作.. 但我很想知道如何实现我在这里尝试获得的功能
非常感谢
按要求修改 这就是我尝试使用它的方式:
首先,我有一个名为GameScene的派生类,它在这里:
class GameScene : public Scene
{
public:
GameScene(void);
void render();
void update();
}
在我的main()函数中:
GameScene gamescene;
ScreenManager manager;
manager.setScene(&gamescene);
答案 0 :(得分:1)
你需要一个具体的派生类:
class MyScene: public Scene {
public:
MyScene(void){}
virtual ~MyScene(void){}
virtual void update();
virtual void render();
};
void setScene(Scene * sc)将是:
void setScene(Scene *sc)
{
curSc = (Scene*)sc;
}
在这种情况下,sc将是MyScene指针。无法创建抽象类实例(即接口),而Scene只是一个接口。
答案 1 :(得分:0)
完全。你做不到
curSc = new Scene
因为它是抽象的。如果您确实要声明Scene
的实例,那么请将其设为非抽象。即实施所有方法。
OR (我认为这是您打算做的)创建一个继承自Scene
并实现所有虚拟方法的类。
class View : public Scene {
public:
View(){}
virtual ~View(void){}
virtual void update();
virtual void render();
};
并实现像
这样的虚拟方法void View::update() {
//
}
void View::render() {
//
}
然后您可以将setScene实现为
void SceneManager::setScene(Scene *sc)
{
curSc = sc;
}
并将其称为
SceneManager smag;
Scene *nsc = new View;
smag.setScene(nsc);
答案 2 :(得分:0)
在这里使用指针并没有错。但与引用不同,指针会促使其用户考虑NULL
。这是警告。引用也可以引用NULL
,但添加防御功能会引导您进入"dark side"。因此,假设引用将引用活动对象是合理的,在这种意义上,引用优于指针。
现在,如果你真的想要保留引用,你可以使用就地构造技术,因为你可以(重新)通过构造函数分配引用:
class SceneManager {
public:
SceneManager(Scene& sc) : curSc(sc) {}
~SceneManager(void);
SceneManager& setScene(Scene &sc) {
SceneManager* cheatCompiler = new(this) SceneManager(sc);
return *cheatCompiler;
}
Scene& curSc;
}
请注意,这是一种古怪的东西。由于编译器总是试图超越我们,我无法保证它在所有情况下都能正常工作。
那说我还是建议你使用指针。如果您不想一直检查NULL,可以实现Null Object Pattern。
之类的功能答案 3 :(得分:0)
您应该使用智能指针,并且不要将成员变量公开。例如:
class Scene {
public:
virtual ~Scene(){}
virtual void update() = 0;
virtual void render() = 0;
};
class MyScene : public Scene {
public:
virtual void update () { /*...*/ }
virtual void render () { /*...*/ }
};
class SceneManager {
public:
SceneManager();
~SceneManager();
void setScene(const std::shared_ptr<Scene> & sc) {
curSc = sc;
}
private:
std::shared_ptr<Scene> curSc;
};
void someProc () {
std::shared_ptr<Scene> sc = std::make_shared<MyScene> ();
auto manager = std::make_shared<SceneManager> ();
manager->setScene (sc);
// ...
}
如果没有智能指针,这看起来就像(但如果不再需要,请记住使用delete
创建的对象new
):
class Scene {
public:
virtual ~Scene(){}
virtual void update() = 0;
virtual void render() = 0;
};
class MyScene : public Scene {
public:
virtual void update () { /*...*/ }
virtual void render () { /*...*/ }
};
class SceneManager {
public:
SceneManager();
~SceneManager();
void setScene(Scene * sc) {
curSc = sc;
}
private:
Scene * curSc;
};
void someProc () {
Scene * sc = new MyScene;
SceneManager * manager = new SceneManager;
manager->setScene (sc);
// ...
}