将 class 方法绑定到另一个 class 的方法

Binding a class method to a method of another class

我有两个 类,其中一个是逻辑,一个是模型。初始化两者后,我想将 b.funB() 绑定到 a.funA() where A a; B b;.

class A{
   public:
     bool funA() { doStuff(); }
}


class B{
   public:
     bool funB();
    
    Template<class T>
    void bindBtoA((bool (B::*fun2)(), bool (T::*fun1)(), T *t){
       funB=std::bind( ?);
       // (fun1, t), (&T::fun1, &t), (T::fun1, t), ... ?
    }
}

如何正确绑定它们并消除“无法转换”错误(我在实际代码中确实使用了 typedef)

可以接受使用 lambda 的答案。但是,funB 需要是可调用的,因为另一个引擎需要获取此 (提示:Q_INVOKABLE),因此对 [=18 使用 std::function =] 可能不适用于我的情况。

您可以通过 std::function 的魔法实现这一点,它会隐藏在 class B 中并类型擦除要调用的函数,从而为您提供通用性寻求.

这是一个完整的示例:

#include <iostream>
#include <functional>

class A
{
public:
    bool funA () { std::cout << "funA\n"; return true; }
};

class B
{
public:
    bool funB ()
    {
        return f ();
    }
    
    template <class T>
    void bindBtoA (bool (T::*fun1) (), T *t)
    {
         f = [t, fun1] { return (t->*fun1) (); };
    }

private:    
    std::function <bool ()> f;
};

int main()
{
    A a;
    B b;
    b.bindBtoA <A> (&A::funA, &a);
    std::cout << b.funB ();
}

Live demo

我认为这适用于 Q_INVOKABLE,但我实际上对此一无所知,因此您必须尝试一下。但如果它确实有效,这是一个很好的方法。

注意: 使用发布的代码,只要 b 还活着,您就有责任保持 a 活着。如果您不能保证这一点,更好的选择是使用 std::shared_ptr 代替。或者复制 abindBtoA 中,如果这对你来说是一个实用的解决方案(我猜它不是)。