传递给协程的临时何时会被销毁?

When do temporaries passed to coroutines get destroyed?

本文关键字:何时会      更新时间:2023-10-16

我对传递给协程任务的临时变量的生存期感到困惑。 请考虑以下示例:

cppcoro::task<> UseObject(Object const& object);
cppcoro::task<> CallUseObject() {
co_await UseObject(Object()); // is this valid?
}

如果这些是返回 void 的函数,那么传递给UseObjectObject()将在分号处被销毁(即在UseObject完成后)。 但是,我不确定这是否同样适用于协程。 通过引用将临时传递给例程是否安全? 如果临时不在分号处,什么时候会被摧毁?

此外,作为健全性检查,是否始终可以安全地编写:

cppcoro::task<> CallUseObject() {
Object stayingalive;
co_await UseObject(stayingalive);
}

既然staying_alive在co_await完成后被摧毁了?

这实际上是当前草案的一个未决问题的主题。引用问题:

目的是创建参数的副本/移动(如果需要),保留确切的类型(包括引用、r 引用等)。11.4.4[dcl.fct.def.coroutine]/11中的措辞似乎没有清楚地表达出来。

基于此,协程框架似乎将捕获对临时帧的引用。

由于co_await是一个表达式,因此临时表达式应该在它出现的完整表达式的末尾被销毁。上面的代码是否安全将取决于所涉及的两个协程的具体实现是否能够安全地co_await引用临时UseObject调用。具体而言,请注意,co_await的作用取决于两者、它所应用的表达式的类型以及它出现的协程的 promise 类型。此外,UseObject(我们不知道它的定义)至少在原则上可以用它给出的参考做各种奇怪的事情......