You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用C++17标准库实现对象间方法的事件绑定及参数自动推导?

C++17实现无占位符的事件-处理器绑定

需求场景

想要实现将一个对象的事件成员方法,绑定到另一个对象的处理成员方法上,期望调用形式简洁直接,比如:

connect(&a, &A::eventA, &b, &B::handlerA);

无需根据事件/处理器的参数数量手动调整绑定代码。

用std::bind的局限

直接用std::bind实现的话,必须显式指定std::placeholders::_1、_2等占位符,不同参数个数的成员函数需要写不同的绑定逻辑,扩展性很差。比如绑定一个单参数方法要写:

std::bind(&B::handlerA, &b, std::placeholders::_1);

如果是双参数方法又要改成std::placeholders::_1, std::placeholders::_2,非常繁琐。

C++17解决方案:带自动推导的lambda实现通用connect

利用C++17的模板参数自动推导特性,结合lambda表达式的完美转发,可以实现一个无需占位符的通用connect函数,自动适配任意参数数量的成员函数:

#include <functional>
#include <iostream>

// 通用connect模板函数
template<typename EventObj, typename EventFunc, typename HandlerObj, typename HandlerFunc>
auto connect(EventObj* event_obj, EventFunc event_func, HandlerObj* handler_obj, HandlerFunc handler_func) {
    return [event_obj, event_func, handler_obj, handler_func](auto&&... args) {
        // 先调用事件方法,再将参数转发给处理方法
        (event_obj->*event_func)(std::forward<decltype(args)>(args)...);
        (handler_obj->*handler_func)(std::forward<decltype(args)>(args)...);
    };
}

// 示例类A(事件触发方)
class A {
public:
    void eventA(int x) {
        std::cout << "Event A triggered with value: " << x << "\n";
    }
    void eventB(std::string msg, double val) {
        std::cout << "Event B triggered: " << msg << ", " << val << "\n";
    }
};

// 示例类B(事件处理方)
class B {
public:
    void handlerA(int x) {
        std::cout << "Handler A processed value: " << x * 2 << "\n";
    }
    void handlerB(std::string msg, double val) {
        std::cout << "Handler B processed: " << msg << " -> " << val + 1.5 << "\n";
    }
};

int main() {
    A a;
    B b;

    // 绑定单参数事件与处理器
    auto bound_eventA = connect(&a, &A::eventA, &b, &B::handlerA);
    bound_eventA(10);

    // 绑定双参数事件与处理器
    auto bound_eventB = connect(&a, &A::eventB, &b, &B::handlerB);
    bound_eventB("Test", 3.2);

    return 0;
}

代码说明

  • 模板函数connect自动推导事件对象、事件方法、处理对象、处理方法的类型,无需手动指定模板参数。
  • 返回的lambda表达式使用auto&&... args实现可变参数的完美转发,适配任意参数数量的成员函数。
  • 调用绑定后的函数时,会先触发事件方法,再将参数转发给处理方法,你可以根据需求调整执行顺序或逻辑。

内容的提问来源于stack exchange,提问作者Maxim

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.09 00:12:45