Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/150.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 游客模式与康斯坦斯_C++_Constants_Visitor - Fatal编程技术网

C++ 游客模式与康斯坦斯

C++ 游客模式与康斯坦斯,c++,constants,visitor,C++,Constants,Visitor,我遇到了一个关于访客模式和稳定性的问题 假设C++中的访问者模式实现了一个小游戏,在游戏中,你可以根据可绘制对象的内部状态在屏幕上画东西,同时运行一个可以改变内部状态的逻辑,几乎可以想象任何游戏。请原谅代码中的任何错误,因为这是动态完成的 //Forward declaration of classes and visitor... //class Game_actor; This one will be abstract, virtual, whatever. class Game_acto

我遇到了一个关于访客模式和稳定性的问题

假设C++中的访问者模式实现了一个小游戏,在游戏中,你可以根据可绘制对象的内部状态在屏幕上画东西,同时运行一个可以改变内部状态的逻辑,几乎可以想象任何游戏。请原谅代码中的任何错误,因为这是动态完成的

//Forward declaration of classes and visitor...

//class Game_actor; This one will be abstract, virtual, whatever.
class Game_actor_item;
class Game_actor_player;
class Game_actor_invisible;

class Visitor
{
    public:
//  virtual void visit(Game_actor& r)=0;
    virtual void visit(Game_actor_player& r)=0;
    virtual void visit(Game_actor_item& r)=0;
    virtual void visit(Game_actor_invisible& r)=0;
};
然后,一些界面,如基础:

//This one defines stuff that can be on the screen.

class Drawable
{
    public:
    virtual void draw(Screen&)=0;
};

//This one defines stuff that changes its state. Let's assume that do_logic 
//returns an integer that means something to the controller and can be 
//interpreted via a long list of "message_codes" (1=Add score, 2=Substract 
//score, 3=Something else...). Each actor will run its logic and return its 
//message, that will be stored and interpreted later. This is mostly crap, 
//I know, but makes for a quick example.

class Game_actor
{
    private:

    float x;
    float y;

    public:
    virtual int do_logic()=0;
    void accept_visitor(Visitor& v)=0;
};
接下来,我们的对象层次结构:项目和播放器是从actor派生的,actor定义了它们内部状态的一部分。当然,它们可以被吸引到屏幕上。有一个特殊的演员不会被画出来,因为它是隐形的,并且控制着其他的东西

class Game_actor_item: public Drawable, public Game_actor
{
    //Lines and lines of code.
    virtual void draw(Screen& s) {/* [...] */}
    virtual int do_logic() {/* [...] */}
};

class Game_actor_player: public Drawable, public Game_actor
{
    //Lines and lines of code.
    virtual void draw(Screen& s) {/* [...] */}
    virtual int do_logic() {/* [...] */}
};

class Game_actor_invisible: public Game_actor
{
    //Lines and lines of code.
    virtual int do_logic() {/* [...] */}
};
最后,游客专业化。我们将定义两个访问者,一个将收集所有可绘制的演员,另一个将向游戏控制器发送消息。可绘制的演员将从 它的基类的向量

class Visitor_drawing:public Visitor
{
    private:
    std::vector<Drawable *> draw_all_these;

    public:
//  virtual void visit(Game_actor& r) 
    virtual void visit(Game_actor_player& r) {draw_all_these.push_back(&r);}
    virtual void visit(Game_actor_item& r) {draw_all_these.push_back(&r);}

    //This one won't be drawn.
    virtual void visit(Game_actor_invisible&) {}

    std::vector<Drawable *> get_me_the_drawables() {return draw_all_these;}
}

class Visitor_logic:public Visitor
{
    private:
    std::vector<int> messages;

    public:
//  virtual void visit(Game_actor& r) 
    virtual void visit(Game_actor_player& r) {messages.push_back(r.do_logic());}
    virtual void visit(Game_actor_item& r) {messages.push_back(r.do_logic());}
    virtual void visit(Game_actor_invisible&) {messages.push_back(r.do_logic());}

    std::vector<int> fetch_me_the_messages() {return messages;}
}
但似乎我必须实现单独的accept_visitor方法,因为编译器不区分调用:

void accept_visitor_const(Const_visitor& v)=0;
void accept_visitor(Non_const_visitor& v)=0;
这导致了基本访问者类中的各种重复,基本上所有内容都要写两次,const和non-const版本,然后在主循环中分离调用:不再有单一的accept\u访问者,您必须提前知道您期望的访问者是什么类型的。副作用是,它确实表明我将接受这个承诺不改变我的内部结构的访问者,这是有点可取的

不管怎样,我是否缺少任何其他不会从根本上改变此设置的选项?。这是一个合适和可取的选择吗


一如往常,请提前致谢。

void accept\u visitor\u const\u visitor&v=0;可为无效接受访问者常数访问者&v常数=0;我认为这是可行的,编译器会选择正确的版本。我现在无法使用该代码访问计算机,但将对其进行测试并尽快报告。谢谢Jarod42。如前所述,我尝试了代码并做了必要的更改。当然,这是有效的,因此se至少不需要知道要调用哪个accept_visitor方法。仍然有一个常量和非常量方法具有相同的主体,但我不认为我会用常量来定义它和非常量。特别是因为该解决方案比当前主体更长!。再次感谢你,伙计。
class Const_visitor
{
    virtual void visit(const Thing&)=0;
};

class Non_const_visitor
{
    virtual void visit(Thing&)=0;
};

class Visitor_drawing:public Const_visitor
{
    virtual void visit(const Thing&)=0;
};

class Visitor_logic:public Non_const_visitor
{
    virtual void visit(Thing&)=0;
};
void accept_visitor_const(Const_visitor& v)=0;
void accept_visitor(Non_const_visitor& v)=0;