1

是否可以使用 Async CTP 来模拟延续和尾递归?

我在想一些事情:

async Task Loop(int count)
{
    if (count == 0)
        retrun;

    await ClearCallStack();
    //is it possible to continue here with a clean call stack?
    Loop(count -1)
}

我想需要一个自定义调度程序等,但有可能吗?(也就是说,它是否可以用于递归而不会破坏调用堆栈)

4

1 回答 1

4

是的,这是完全可能的。

在最新的 Async CTP(VS2010 SP1 的刷新)中,单元测试示例中有一个“GeneralThreadAffineContext”类(在 VB 或 C# 中)。这为仅以通用线程仿射方式运行异步方法提供了必要的帮助程序代码。

通过线程关联,我们的意思是异步延续在与原始线程相同的上下文中进行处理,类似于 WinForms/WPF 的行为,但不会启动真正的 WPF 或 WinForms 消息循环。

Task.Yield()的设计是将当前方法的其余部分推迟到 SynchronizationContext,因此您甚至不需要编写自己的await ClearCallStack(). 相反,您的样本将归结为:

async Task DoLoop(int count)
{
    // yield first if you want to ensure your entire body is in a continuation
    // Final method will be off of Task, but you need to use TaskEx for the CTP
    await TaskEx.Yield();

    if (count == 0)
        return;

    //is it possible to continue here with a clean call stack?
    DoLoop(count -1)
}

void Loop(int count)
{
    // This is a stub helper to make DoLoop appear synchronous. Even though
    // DoLoop is expressed recursively, no two frames of DoLoop will execute
    // their bodies simultaneously
    GeneralThreadAffineContext.Run(async () => { return DoLoop(count); });
}
于 2011-04-14T20:11:55.540 回答