Asynchronous 异步{try…finally…}的finally没有被调用的可能原因是什么?涉及的处方

Asynchronous 异步{try…finally…}的finally没有被调用的可能原因是什么?涉及的处方,asynchronous,f#,system.reactive,cancellation,Asynchronous,F#,System.reactive,Cancellation,我有这样的想法: let a = async { try do! Async.AwaitTask someTask finally // clean up } Async.Start (a, cancellationTokenSource.Token) 当在a中等待的任务完成时,最后执行块并完成清理,但当asynca由于调用cancellationTokenSource而被取消时,不会执行清理。事实

我有这样的想法:

let a =
    async {
        try
            do! Async.AwaitTask someTask
        finally
            // clean up
    }
Async.Start (a, cancellationTokenSource.Token)
当在
a
中等待的任务完成时,
最后执行
块并完成清理,但当async
a
由于调用
cancellationTokenSource
而被取消时,不会执行清理。事实上,我怀疑
a
一直在运行

我真的没有线索,所以这里有一个初步的猜测:不,我真的没有猜测

编辑

问题似乎出在
a
正在等待的任务中。 如果
someTask
是:

Async.Ignore (Async.AwaitIAsyncResult <| Task.Delay(5000))
vm
是一个视图模型。
Finished
是一个事件。基本上,我希望
a
由于取消或
Finished
发生在
vm
中而结束)


然后,
a
拒绝被取消,或者最后被跳过,我不知道是哪个。

在.Net中取消是合作的。这意味着,一旦任务开始,发出
CancellationToken
的信号就没有实际效果,除非您对其进行监控


要启用取消,您需要在实际操作中选中
CancellationToken.IsCancellationRequested
,如果为true,则结束它。或者您可以调用
CancellationToken.ThrowIfCancellationRequested
以引发结束操作的异常。

您需要将
CancellationToken
传递给
ToTask()
,否则无法取消


使用。

您能发布完整的样本吗?请注意,任务需要测试其是否已取消。如果没有,就不会取消。你是对的。我通过将取消令牌传递给
ToTask
解决了这个问题。我遇到了双重麻烦,因为我没有意识到Async.CancellationToken返回一个Async,当传递给ToTask时,它调用了错误的重载--晚了一秒!但是是的,这就是解决问题的方法。事实上,你的答案更明确,所以…我真正的问题是我调用了错误的重载。我没有意识到,我也必须让!ct=Async.CancellationToken
vm.Finished.Select(ignore).FirstAsync().ToTask()