我注意到在Boost.Coroutine2 for C ++中删除了对对称协程的支持,所以我想了解 - 两者之间有什么区别?
答案 0 :(得分:12)
AnaLúciadeMoura和Roberto Ierusalimschy在他们的论文“Revisiting Coroutines”中特别描述了对称和不对称协程之间的区别:
众所周知的协程分类涉及所提供的控制转移操作,并区分对称和非对称协同程序的概念。对称协程设备提供单一的控制转移操作,允许协同程序明确地在它们之间传递控制。非对称协程机制(通常表示为半对称或半协程)提供两个控制转移操作:一个用于调用协程,一个用于挂起,后者返回控制到协程调用者。虽然对称协程在相同的层次级别运行,但不对称协程可以被视为从属于其调用者,它们之间的关系有点类似于被调用和调用例程之间的关系。
支持并发编程的协同机制通常提供对称协程来表示独立的执行单元,如Modula-2。另一方面,旨在实现产生值序列的构建体的协同机制通常提供不对称的协同程序。此类构造的示例是迭代器和生成器。
(引文省略)
在非对称协程模型中,“不对称”指的是协程之间存在类似堆栈的调用者 - 被调用者关系。协程可以调用另一个协程,也可以通过控制其调用者来暂停自身,通常也会同时为调用者产生一个值。
在对称协程模型中,协程可以无限制地控制任何其他协程。
这两个模型实际上具有相同的表现力;即,可以使用对称协程来实现不对称协程,反之亦然。 (参见Giovanni P. Deretta撰写的Symmetric coroutines,两种协程之间的转换。)因此,Moura和Ierusalimschy写道:“提供这两种结构只会使[coroutine]机制的语义复杂化,没有增加其表现力。“
Coroutine2的开发人员决定不在库中提供对称协同程序,因为他们认为boost::context::execution_context
(Boost.Context的一部分)更好地实现了对称协程功能:http://lists.boost.org/Archives/boost/2015/06/223701.php
答案 1 :(得分:10)
协同程序在来电者和被叫者之间切换,例如你进入corotuine-function并切换回调用代码。通常(不对称)协程有两个用于此目的的函数:
因为您有两个函数来切换上下文,所以它被称为非对称的。 对称协同程序只有一个函数可以暂停当前上下文并恢复另一个上下文。请注意,您必须指定下一个必须恢复的对称协程。
对称协程可用于实现用户域线程(对称协程代表用户空间线程;调度程序从一个跳转到下一个symmtric协程,例如调度下一个用户域线程)<比非对称协程更强>更有效率 这是显而易见的,因为对称协程不需要跳回调用者以恢复下一个用户域线程。 非对称协程需要比对称协程更多的上下文切换才能实现相同的功能。
对称协同程序 - 对称上下文切换 - 可以通过诸如使用当前延续的调用等概念更好地表示。 (Scheme,Ruby ......)。 boost.context通过 callcc()/ continuation 的实现支持这个概念。 因此boost.coroutine2不提供对称的协程API - 但boost.coroutine2的不对称协程是用boost.context的 callcc()/ continuation 实现的。