无拷贝构造函数时,如何在condition_variable wait_until的lambda中使用类实例?
解决方案:无需拷贝构造函数实现需求
问题根源
原代码编译失败的核心原因是:lambda表达式使用值捕获demo,这会强制触发Demo类的拷贝构造函数,但你的Demo类未提供该函数(默认拷贝构造可能被删除),因此编译报错。
关键修改(无需添加拷贝构造)
- 改用引用捕获
demo,避免拷贝操作; - 修正严重逻辑错误:将互斥量
cv_m移到循环外部——条件变量的互斥量必须与共享数据(Demo的事件号)绑定,所有访问/修改该共享数据的线程都要使用同一个互斥量,否则会出现数据竞争或条件变量唤醒失效。
修改后的代码示例
int main() { Demo demo; // Demo类实例 std::mutex cv_m; // 互斥量移到循环外,与共享数据绑定 const int target_event = 20; // 目标事件号 while(1) { std::unique_lock<std::mutex> lock(cv_m); std::chrono::seconds time_period(20); auto time_duration = std::chrono::system_clock::now() + time_period; // 引用捕获demo,避免拷贝;同时确保访问事件号时持有互斥量 if(demo.cond_var.wait_until(lock, time_duration, [&demo, target_event](){ return demo.getEventNum() == target_event; })){ std::cout<<"到达目标事件号!"<<std::endl; break; } else{ std::cout<<"等待超时!"<<std::endl; break; } } }
额外注意事项
必须确保其他线程更新Demo的事件号时,也持有同一个cv_m互斥量,否则getEventNum()的访问会存在数据竞争,导致未定义行为。如果Demo的getEventNum()成员函数本身没有加锁逻辑,当前代码中持有cv_m的unique_lock已经保证了访问的线程安全性。
内容的提问来源于stack exchange,提问作者issac
相关产品推荐
相关产品推荐

