我正在创建一些将被分离的std :: threads。我想让这些运行很长时间,并希望这些能够自己处理异常。
我使用std :: thread(Function)创建了一个线程,并在释放互斥锁之前调用了detach,并且函数执行了以下操作:
void BlockStart() noexcept {
std::lock_guard<std::mutex> sync(lock);
}
void Function()
{
BlockStart();
try
{
throw;
}
catch(...)
{
std::cerr << "Caught something...\n";
}
}
每次运行此代码时,都不会调用异常处理程序。调用std :: terminate()的默认处理程序,它调用abort。
如何获得std :: thread启动线程来处理异常?
答案 0 :(得分:3)
根据这个问题的答案:https://stackoverflow.com/a/5378736/1619294
如果你自己做
throw;
,并且没有重新抛出的当前例外,那么程序会突然结束。 (更具体地说,调用terminate()
。)
您可能想要执行类似
的操作void Function()
{
try
{
SomeOtherFunction();
}
catch(...)
{
std::cerr << "Caught something...\n";
}
}
另请注意,BlockStart()
函数内的锁定保护+互斥锁只会在函数的持续时间内阻塞,并且在返回后不会保留。解决方案是将锁定保护锁定在Function()
void Function() {
std::lock_guard<std::mutex> sync(lock);
...
答案 1 :(得分:1)
单独调用throw
会重新抛出当前异常,但只有在catch
块内部调用时才有效。如果您在没有当前例外的情况下尝试在throw
块内自行调用try
,则会调用terminate()
并且您的应用已停止。您必须告诉throw
WHAT 在try
块内时抛出,例如:
void Function()
{
BlockStart();
try
{
throw std::runtime_error("something bad happened");
}
catch(const std::exception& e)
{
std::cerr << "Caught something... " << e.what() << std::endl;
}
}
此外,在std::lock_guard
内使用BlockStart()
也没用。 sync
是一个局部变量,因此当BlockStart()
退出时,它将超出范围并释放互斥锁。只有当互斥锁被锁定时它才真正起作用才有意义使用它,例如:
void BlockStart() noexcept
{
std::lock_guard<std::mutex> sync(lock);
// do something here while the mutex is locked...
}