测试含std::function参数的私有回调方法遇类型匹配错误求助
问题分析与解决方案
你的问题核心是类型不匹配:生产代码中std::bind生成的函数签名,和测试代码里m_Callback的签名完全不一致,导致Google Mock的SaveArg无法完成赋值操作。
为什么会报错?
先拆解你的生产代码逻辑:
void MyClass::initialize(const Callback callback) { m_SomeClass->registerCallback(std::bind(&MyClass::callbackMethod, this, callback)); }
这里的std::bind把callbackMethod的两个参数(this指针和callback)都固定死了,最终生成的是一个无参可调用对象(签名是void())——因为callbackMethod需要的参数已经被绑定好了,不需要再传入任何值。
但你的测试代码里,m_Callback的类型是std::function<void(const Callback callback)>,也就是一个需要接收Callback参数的函数类型。这俩类型完全不兼容,SaveArg尝试把std::function<void()>赋值给std::function<void(const Callback)>时,就触发了模板推导失败的错误,也就是你看到的报错信息。
解决方案
根据你的测试目标,分两种情况处理:
方案1:保持生产代码逻辑不变(绑定固定的callback)
如果你的业务逻辑就是要把initialize传入的callback固定绑定给callbackMethod,那只需要调整测试代码的m_Callback类型:
- 修改测试类的成员变量:
std::function<void()> m_Callback; - 捕获后直接调用无参函数,就能触发
callbackMethod并传入绑定好的callback:// 初始化测试对象,传入测试用的Callback auto testCallback = [](){ /* 测试逻辑 */ }; myClass->initialize(testCallback); // 调用捕获的回调,触发私有方法callbackMethod m_Callback(); // 这里可以验证callbackMethod的行为,比如是否正确执行了testCallback
方案2:让callbackMethod接收动态传入的Callback
如果你的测试目标是给callbackMethod传入不同的Callback参数,需要修改生产代码的bind逻辑,使用占位符保留参数:
- 修改生产代码的
initialize方法:void MyClass::initialize() { // 使用std::placeholders::_1保留参数,让registerCallback的调用者传入Callback m_SomeClass->registerCallback(std::bind(&MyClass::callbackMethod, this, std::placeholders::_1)); } - 此时你的测试代码无需修改
m_Callback类型,SaveArg可以正常工作,之后可以手动传入不同的测试Callback:// 初始化测试对象 myClass->initialize(); // 传入自定义的测试Callback,触发私有方法 auto testCallback1 = [](){ /* 测试逻辑1 */ }; m_Callback(testCallback1); auto testCallback2 = [](){ /* 测试逻辑2 */ }; m_Callback(testCallback2); // 分别验证两种场景下的行为
内容的提问来源于stack exchange,提问作者Qwer
相关产品推荐
相关产品推荐

