suspendfuntestThree(param: Int) { val result = suspendCoroutine<Int> { continuation -> println("continuation is $continuation") continuation.resumeWith(Result.success(param)) } println("result is $result") }
internalclassCombinedContext( privateval left: CoroutineContext, privateval element: Element ) : CoroutineContext, Serializable { overridefun<E : Element>get(key: Key<E>): E? { var cur = this while (true) { cur.element[key]?.let { return it } val next = cur.left if (next is CombinedContext) { cur = next } else { return next[key] } } } }
示例
规则 1:相同 Key 的元素,右边的覆盖左边的
1 2 3 4 5
val context1 = Job() + CoroutineName("First") val context2 = CoroutineName("Second") + Dispatchers.IO
val result = context1 + context2 // 结果包含:Job(来自context1), Dispatchers.IO(来自context2), CoroutineName("Second")(来自context2,覆盖了context1的)
规则 2:EmptyCoroutineContext 是中性元素
1 2 3
val context = Dispatchers.IO + CoroutineName("Test") val result1 = context + EmptyCoroutineContext // 等于 context val result2 = EmptyCoroutineContext + context // 等于 context
publicoperatorfunplus(context: CoroutineContext): CoroutineContext = if (context === EmptyCoroutineContext) thiselse// fast path -- avoid lambda creation context.fold(this) { acc, element -> val removed = acc.minusKey(element.key) if (removed === EmptyCoroutineContext) element else { // make sure interceptor is always last in the context (and thus is fast to get when present) val interceptor = removed[ContinuationInterceptor] if (interceptor == null) CombinedContext(removed, element) else { val left = removed.minusKey(ContinuationInterceptor) if (left === EmptyCoroutineContext) CombinedContext(element, interceptor) else CombinedContext(CombinedContext(left, element), interceptor) } } }