【问题标题】:Implementig a C++ State Machine. How to solve Wpmf-convesion Warning?实现 C++ 状态机。如何解决 Wpmf 转换警告?
【发布时间】:2020-03-02 10:14:33
【问题描述】:

我正在尝试在 C++ 中实现,此链接中描述的 C 语言状态机:https://barrgroup.com/Embedded-Systems/How-To/Coding-State-Machines

我创建了一个 Fsm 类,它实现了状态机的行为,以及一个 Machine 类,它的方法将是状态。

代码有效,但是当我尝试将 Machine 方法的内存地址保存为 State 状态时,它会生成警告 (-Wpmf-conversions)

class Fsm
{
public:
    typedef void (*State)();
private:
    State state__;
public:
    Fsm(State state);
    void dispatch();
}; 

Fsm::Fsm(State state)
{
    state__ = state ;
} //Fsm

void Fsm::dispatch()
{
    (*state__)() ;
}



class Machine : public Fsm
{
public:
    Machine() : Fsm((State)&Machine::initial) {}       // ctor
}; 

我希望解决 -Wpmf-conversions 警告。

【问题讨论】:

  • State 是一个普通的函数指针,而不是指向成员函数的指针。这两个是非常不同的。您不妨参考您最喜欢的 C++ 教科书了解详细信息。
  • Fsm((State)&Machine::initial -- 你不应该像这样掩盖编译器错误。如果您不对State 进行C 风格转换,编译器会告诉您问题出在哪里。删除演员表,阅读错误,并阅读@IgorTandetnik 之前的评论
  • 我没有掩盖编译器错误。使用嵌入式系统时,New 和 Delete 运算符不可用。因此,就像 malloc 和 free 必须用于处理对象一样,使用传统的状态模式为每个状态实例化新对象并不是一个好主意。所以我正在使用 Barr Group 提出的这个状态机解决方案:barrgroup.com/Embedded-Systems/How-To/Coding-State-Machines。该示例也使用了该转换,但我认为他们只是忽略了该警告
  • 如果从逻辑上看,这个回调是如何工作的?要调用非静态成员函数,需要在调用中指定对象。您不能简单地说 (*func)() 或类似的词来拨打电话。语法为(object->*func)()(object.*func)()。那么object 来自哪里?

标签: c++ casting function-pointers compiler-warnings state-machine


【解决方案1】:

State 确实对应于函数指针。

很遗憾,您没有在代码中提供initial 的定义。所以这是一个小小的猜测。但是在构造函数的参数(State)&Machine::initial 中,您似乎认为它是一个静态成员函数。

编译时没有错误或警告:

class Machine : public Fsm
{
    static void initial();    // make sure it's static 
public:
    Machine() : Fsm((State)&Machine::initial) {}       // ctor
}; 

现在,如果您想要一个指向成员函数的指针,那就另当别论了。首先,您需要相应地定义State

typedef void (Fsm::*State)();

那么dispatch必须调用一个成员函数:

void Fsm::dispatch()
{
    (this->*state__)() ;
}

唯一的问题可能是您使用基成员函数指针调用派生成员函数指针。幸运的是,正如this excellent answer 中所解释的那样,这可以保证工作。

【讨论】:

  • 谢谢!!完全有效。第二个答案是我需要的。我正在使用指向成员函数的指针。
猜你喜欢
  • 2022-08-24
  • 2013-04-29
  • 1970-01-01
  • 2012-11-02
  • 1970-01-01
  • 1970-01-01
  • 2010-10-05
  • 2012-06-14
相关资源
最近更新 更多