代码之家  ›  专栏  ›  技术社区  ›  Spencer Michaels

从同一类的两个不同模板副本继承时重载

  •  0
  • Spencer Michaels  · 技术社区  · 6 年前

    我正在为一个游戏编写一个输入处理系统,我想将其扩展到任意事件类型。我想设计一个类似接口的规范,允许我强制要求某些对象处理某些事件;例如,通过以下方式 class Player : public EventHandler<KeyboardEvent> . 我提议的设计如下。

    template <class T>
    class EventHandler {
    public:
        void handleEvent(T event) { doHandleEvent(event); };
    private:
        virtual void doHandleEvent(T event) {};
    };
    
    class InputHandler : public EventHandler<Action>, public EventHandler<CursorEvent> {};
    

    然而,在我打电话的时候 InputHandler::handle() ,以上产生以下错误。看来 handleEvent() 对于的两个模板版本 EventHandler 被视为相同的函数。我的印象是 handleEvent 如果参数类型不同,则结果应该是 InputHandler 有一个重载函数和两种可能的参数类型。

    为什么C++不允许这样做,还有什么更好的方法可以替代我正在尝试的方法?我怀疑以上可能不是好做法。

    /Users/smichaels/Projects/danmaku/src/SDL/Input.cpp:35:34: error: member 'handleEvent' found in multiple base classes
          of different types
                    if (act) handler.handleEvent(act.get());
                                     ^
    /Users/smichaels/Projects/danmaku/src/SDL/../Input/InputHandler.hpp:15:14: note: member found by ambiguous name lookup
            void handleEvent(T event) { doHandleEvent(event); };
                 ^
    /Users/smichaels/Projects/danmaku/src/SDL/../Input/InputHandler.hpp:15:14: note: member found by ambiguous name lookup
    
    1 回复  |  直到 6 年前
        1
  •  1
  •   Yakk - Adam Nevraumont    6 年前
    class InputHandler :
      public EventHandler<Action>,
      public EventHandler<CursorEvent>
    {
    public:
      using EventHandler<Action>::handleEvent;
      using EventHandler<CursorEvent>::handleEvent;
    };
    

    在里面 你可以改为写:

    template<class...Bases>
    struct ManyHandler:Bases...{
      using Bases::handleEvent...;
    };
    template<class...Events>
    using EventsHandler=ManyHandler< EvendHandler<Events>...>;
    

    然后

    class InputHandler : public EventsHandler<Actions, CursorEvent >{};
    

    如果你也有

    class OutputHandler : public EventsHandler< Messages, Sounds >{};
    

    我们可以写

    class IoHandler : public ManyHandler< InputHandler, OutputHandler > {};