为什么这个代码捕获块不执行
Why does this code catch block not execute?
catch 处理程序未运行。但是为什么?
如果thread t
在try
块之前启动,则 catch 处理程序将运行。
与抛出的类型不匹配,程序将退出,说明线程以未捕获的异常终止,这表明异常已处理,但 catch 块未运行。
#include <iostream>
#include <thread>
using namespace std;
void do_work() {}
int main() {
std::cerr << "RUNNING" << std::endl;
try {
thread t(do_work);
std::cerr << "THROWING" << std::endl;
throw logic_error("something went wrong");
} catch (logic_error e) {
std::cerr << "GOTCHA" << std::endl;
}
return 0;
}
编译命令:
c++ -std=c++14 -pthread -pedantic -Wall -Wextra -O0 scratch.cpp -o scratch
你忘了加入线程:
try {
thread t(do_work);
t.join(); // <<< add this
std::cerr << "THROWING" << std::endl;
throw logic_error("something went wrong");
} catch (logic_error e) {
std::cerr << "GOTCHA" << std::endl;
}
超出范围的可联接线程会导致调用terminate
。因此,您需要在超出范围之前调用join
或detach
。
在 C++11, 30.3.1.3 中,标准说线程析构函数
如果 joinable() 则终止 (),否则没有效果。[注意:在其析构函数中隐式分离或加入 joinable() 线程都可能导致仅在引发异常时才遇到难以调试的正确性(用于分离)或性能(用于连接)错误。因此,程序员必须确保析构函数永远不会在线程仍可连接时执行。—尾注]
因此,一旦调用线程析构函数,程序就会terminate
,因为作用域结束并且永远不会执行catch
逻辑。
如果您希望程序在线程范围之外捕获异常,但在线程仍可连接时抛出,则需要在线程本身的范围内捕获它,连接或分离线程并重新抛出已捕获的任何内容。
try
{
std::thread t(foo);
try
{
std::cerr << "THROWING" << std::endl;
throw std::logic_error("something went wrong");
}
catch (...) // catch everything
{
t.join(); // join thread
throw; // rethrow
}
t.join();
}
catch (std::logic_error & e)
{
std::cerr << "GOTCHA: " << e.what() << std::endl;
}
相关文章:
- 需要将此代码更改为执行代码
- 当前不会命中断点。没有调试器目标代码类型的可执行代码与此文件关联
- 单步执行代码时重复上一行
- 如何使用介子在C++中执行代码覆盖?
- Visual Studio 2017,C++,在单步执行代码时指向错误的行
- 在 R 中执行C++代码
- 通过 dll 注入在主线程中执行代码
- 无法在 c++ 中循环后执行代码
- 执行C 代码时快速频繁的文件访问
- 执行 C++ 代码后出错
- 一个人如何从代表函数的字符串中执行运行时执行C 代码
- 是否可以在程序崩溃后执行代码?
- 第一次在 Linux 上执行 c++ 代码的时间非常慢
- 计算 JSON 中的条目数并相应地执行代码
- 将在 CATCH 块之后执行代码
- 分析执行C++代码的每一行所花费的确切时间
- 我在执行代码时不断得到"Bus Error"?
- c while()..执行代码行的条件
- 从并行线程在主 Maya 线程上执行代码
- 在调用GNUPLOT之后,如何继续执行C 代码