gpt4 book ai didi

c# - 如何使用 call/cc 实现 c# 5.0 中的新异步功能?

转载 作者:IT王子 更新时间:2023-10-29 04:42:22 26 4
gpt4 key购买 nike

我一直在关注有关 c# 5.0 中新的 async 功能的新公告。我对连续传递样式以及新的 c# 编译器对类似来自 Eric Lippert's post 的代码片段的代码的转换有基本的了解。 :

async void ArchiveDocuments(List<Url> urls)
{
Task archive = null;
for(int i = 0; i < urls.Count; ++i)
{
var document = await FetchAsync(urls[i]);
if (archive != null)
await archive;
archive = ArchiveAsync(document);
}
}

我知道有些语言通过 call-with-current-continuation (callcc) 在本地实现延续,但我真的不明白它是如何工作的或者它到底做了什么。

所以问题来了:如果 Anders 等人。决定硬着头皮在 c# 5.0 中实现 callcc 而不是 async/await 特例,上面的代码片段会是什么样子?

最佳答案

原答案:

据我了解,您的问题是“如果不是专门为基于任务的异步实现“等待”,而是实现了 call-with-current-continuation 的更通用的控制流操作呢?”

好吧,首先让我们考虑一下“await”的作用。 “await”采用 Task<T> 类型的表达式,获得一个等待者,并用当前的继续调用等待者:

await FooAsync()

变得有效

var task = FooAsync();
var awaiter = task.GetAwaiter();
awaiter.BeginAwait(somehow get the current continuation);

现在假设我们有一个运算符 callcc它以一个方法作为参数,并使用当前的延续调用该方法。看起来像这样:

var task = FooAsync();
var awaiter = task.GetAwaiter();
callcc awaiter.BeginAwait;

换句话说:

await FooAsync()

不过是

callcc FooAsync().GetAwaiter().BeginAwait;

这是否回答了您的问题?


更新#1:

正如一位评论者所指出的,下面的答案假设代码生成模式来自异步/等待功能的“技术预览”版本。实际上,我们在该功能的测试版中生成了略有不同的代码,尽管逻辑上它是相同的。目前的代码生成器是这样的:

var task = FooAsync();
var awaiter = task.GetAwaiter();
if (!awaiter.IsCompleted)
{
awaiter.OnCompleted(somehow get the current continuation);
// control now returns to the caller; when the task is complete control resumes...
}
// ... here:
result = awaiter.GetResult();
// And now the task builder for the current method is updated with the result.

请注意,这有点复杂,并且处理您正在“等待”已经计算出的结果的情况。如果您等待的结果实际上已经为您缓存在内存中,则无需经历所有将控制权交给调用者并在您停止的地方重新开始的繁琐操作。

因此,“await”和“callcc”之间的联系并不像预览版中那么简单,但仍然很明显,我们本质上是在等待者的“OnCompleted”方法上执行 callcc。如果没有必要,我们只是不执行 callcc。


更新#2:

作为这个答案

https://stackoverflow.com/a/9826822/88656

Timwi 指出,call/cc 和 await 的语义并不完全相同; “真正的”调用/cc 要求我们“捕获”一个方法的整个延续包括它的整个调用堆栈,或者等效地整个程序被重写为延续传球风格。

“等待”功能更像是“合作调用/抄送”; continuation 仅捕获“当前 任务返回方法 在等待点下一步要做什么?”如果任务返回方法的调用者要在任务完成后做一些有趣的事情,那么它可以自由地将它的延续注册为任务的延续。

关于c# - 如何使用 call/cc 实现 c# 5.0 中的新异步功能?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/4070237/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com