是否有必要在 std::coroutine_handle 上调用 destroy?
Is it necessary to call destroy on a std::coroutine_handle?
std::coroutine_handle
是C++20新协程的重要组成部分。例如,生成器经常(总是?)使用它。在我看到的所有例子中,句柄都是在协程的析构函数中手动销毁的:
struct Generator {
// Other stuff...
std::coroutine_handle<promise_type> ch;
~Generator() {
if (ch) ch.destroy();
}
}
这真的有必要吗?如果是,为什么 coroutine_handle
还没有完成,是否有 coroutine_handle
的 RAII 版本以这种方式运行,如果我们省略 destroy
调用会发生什么?
示例:
- https://en.cppreference.com/w/cpp/coroutine/coroutine_handle (Thanks 463035818_is_not_a_number)
- C++20 标准在 9.5.4.10 示例 2 中也提到了它(在 N4892 上检查过)。
- (德语)https://www.heise.de/developer/artikel/Ein-unendlicher-Datenstrom-dank-Coroutinen-in-C-20-5991142.html
- https://www.scs.stanford.edu/~dm/blog/c++-coroutines.html - 提到如果不调用它会泄漏,但没有引用标准中的段落或为什么不在
std::coroutine_handle
的析构函数中调用它。
这是因为您希望协同程序的寿命超过其句柄,句柄应该非拥有。句柄只是一个“视图”,很像 std::string_view -> std::string
。如果 std::string_view
超出范围,您不希望 std::string
自行销毁。
如果您确实想要这种行为,围绕它创建自己的包装器将是微不足道的。
也就是说,标准 specifies:
The coroutine state is destroyed when control flows off the end of the
coroutine or the destroy
member function
([coroutine.handle.resumption])
of a coroutine handle
([coroutine.handle])
that refers to the coroutine is invoked.
协程状态将在完成后自行清理运行,因此它不会泄漏,除非控制没有从末端流出。
当然,在生成器的情况下,控制通常不会从末尾流出,因此程序员必须手动销毁协程。协程有多种用途,因此标准不能真正无条件地强制执行句柄析构函数调用 destroy()
.
std::coroutine_handle
是C++20新协程的重要组成部分。例如,生成器经常(总是?)使用它。在我看到的所有例子中,句柄都是在协程的析构函数中手动销毁的:
struct Generator {
// Other stuff...
std::coroutine_handle<promise_type> ch;
~Generator() {
if (ch) ch.destroy();
}
}
这真的有必要吗?如果是,为什么 coroutine_handle
还没有完成,是否有 coroutine_handle
的 RAII 版本以这种方式运行,如果我们省略 destroy
调用会发生什么?
示例:
- https://en.cppreference.com/w/cpp/coroutine/coroutine_handle (Thanks 463035818_is_not_a_number)
- C++20 标准在 9.5.4.10 示例 2 中也提到了它(在 N4892 上检查过)。
- (德语)https://www.heise.de/developer/artikel/Ein-unendlicher-Datenstrom-dank-Coroutinen-in-C-20-5991142.html
- https://www.scs.stanford.edu/~dm/blog/c++-coroutines.html - 提到如果不调用它会泄漏,但没有引用标准中的段落或为什么不在
std::coroutine_handle
的析构函数中调用它。
这是因为您希望协同程序的寿命超过其句柄,句柄应该非拥有。句柄只是一个“视图”,很像 std::string_view -> std::string
。如果 std::string_view
超出范围,您不希望 std::string
自行销毁。
如果您确实想要这种行为,围绕它创建自己的包装器将是微不足道的。
也就是说,标准 specifies:
The coroutine state is destroyed when control flows off the end of the coroutine or the
destroy
member function([coroutine.handle.resumption])
of a coroutine handle([coroutine.handle])
that refers to the coroutine is invoked.
协程状态将在完成后自行清理运行,因此它不会泄漏,除非控制没有从末端流出。
当然,在生成器的情况下,控制通常不会从末尾流出,因此程序员必须手动销毁协程。协程有多种用途,因此标准不能真正无条件地强制执行句柄析构函数调用 destroy()
.