Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/153.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++ 存储/转换函数指向函数的指针<;void()>;_C++ - Fatal编程技术网

C++ 存储/转换函数指向函数的指针<;void()>;

C++ 存储/转换函数指向函数的指针<;void()>;,c++,C++,我有两个班,比如说A和B;我想在a中的包装器函数中存储一个B的函数指针 最终的目标是能够在A中的多个位置调用OnRender(),但是OnRender()是在运行时定义的(比如我想在许多B中选择一个) 这怎么可能呢 class A { public: function<void()> OnRender{}; // I want to use this void (B::*OnRender)(){}; // I want to avoid this } class B

我有两个班,比如说A和B;我想在a中的包装器
函数
中存储一个B的函数指针

最终的目标是能够在A中的多个位置调用
OnRender()
,但是
OnRender()
是在运行时定义的(比如我想在许多B中选择一个)

这怎么可能呢

class A
{
public:
    function<void()> OnRender{}; // I want to use this
    void (B::*OnRender)(){}; // I want to avoid this
}

class B
{
public:
    auto SomeJob() -> void;
}
但我也希望避免在A中引用类B

回答:

我可以像这样存储lambda:

someA.OnRender = &B::SomeJob;
// OK if I use void (B::*OnRender)(){};
someIntanceOfA.OnRender = [&](){ someB->SomeJob(); };
// OK if I use function<void()> OnRender{};

指向非静态类成员方法的函数指针不能类型转换为普通的非类-方法函数指针。如果这样做,这是一种未定义的行为,肯定会导致崩溃。
原因是,调用该类的方法需要该类的对象

传统的指向成员语法的指针更好

参考:


不能,因为C++根本不这样工作。甚至连
&B::SomeJob
也不起作用,因为它不是函数指针,因为
SomeJob()
不是函数。这是一个类方法。差别很大。请参阅C++书籍了解更多信息。C++的解决方案通常不涉及函数函数指针,它不是函数式编程语言。考虑使用模板。@ SAMVARSHIVCHK我可以存储lambda。在C++中没有多个函数可以从中选择,有多个子类实现不同于虚拟函数,让C++为你做这项工作。您的建议是重新发明类继承,但要以笨拙的方式进行。有几十种方法可以解决这个问题,它们不需要函数指针。@Soleil这更好!你看过Qt(我不是说它好)了吗?你能重新开始这个问题吗?在函数中存储lambda实际上工作得很好,这正是我想要的答案。@Soleil,这很危险,因为当lambda实际调用时,对象可能存在,也可能不存在。因此,在这种情况下必须避免通过引用传递。传递值使本地副本变得毫无用处。只是编译并不能解决问题。你能不能请中庸重新开张。我不确定,如果你的问题与其他帖子不同,我在我的答案中链接了。我们可以添加更多代码来解决不存在的情况,在我的情况下,它是已知存在的。我投票赞成重新开放;我的情况不同;我可能会以哪种方式进一步发展。
someA.OnRender = [&](){ if(somB != nullptr) someB->SomeJob(); };