gpt4 book ai didi

c# - 如何同步运行延续任务?

转载 作者:太空宇宙 更新时间:2023-11-03 21:17:00 25 4
gpt4 key购买 nike

我声明了一个应该异步运行 Task 的方法,然后,当 Task 完成时,同步 运行指定的委托(delegate)。

C# 示例:

private void WaitUntilLoadedAsync(Process p, Action callback, int timeout = 1500)
{
Task.Factory.StartNew(() => ProcessUtil.WaitUntilLoaded(p, timeout)).
ContinueWith(() => callback.Invoke()).RunSynchronously();

}

VB.Net 示例:

Private Sub WaitUntilLoadedAsync(ByVal p As Process,
ByVal callback As Action,
Optional ByVal timeout As Integer = 1500)

Task.Factory.StartNew(Sub() ProcessUtil.WaitUntilLoaded(p, timeout)).
ContinueWith(Sub() callback.Invoke()).RunSynchronously()

End Sub

但是,RunSynchronously 方法抛出一个 System.InvalidOperationException 异常,告诉我无法同步运行延续 Task

那我该怎么做呢?

备注:

  • 我能够支持Async/Await 解决方案。

  • 我将保留我的方法的“微小”逻辑或圈复杂度,我的意思是,它只是一个我在其上传递 Acton 的方法,没有在方法外部声明任何委托(delegate)或其他可能导致最终用户编写的不仅仅是 Action 的复杂内容。该方法本身应自动执行所有必需的操作以同步执行该连续任务,外部没有复杂性。

最佳答案

因此,正如我从问题和评论中了解到的那样,您想在线程池线程(后台线程)上运行任务 1,并希望在 UI 上运行任务 2(它是任务 1 的延续)线程。

这里是你如何做到的:

private void WaitUntilLoadedAsync(Process p, Action callback, int timeout = 1500)
{
var thread_scheduler = TaskScheduler.FromCurrentSynchronizationContext();

Task.Factory.StartNew(() => ProcessUtil.WaitUntilLoaded(p, timeout)).
ContinueWith(t => callback.Invoke(), CancellationToken.None, TaskContinuationOptions.None,
thread_scheduler);
}

这段代码的作用是要求 TPL 在将在 UI 线程中执行任务的调度程序上运行延续任务。

这假定从 UI 线程调用 WaitUntilLoadedAsync。如果不是这种情况,只需将 thread_schedular 设置为实例变量(或在可从此方法访问的某个范围内),并确保从 UI 线程对其进行初始化。

请注意,控件将立即返回给 WaitUntilLoadedAsync 的调用者,回调将在任务 1 完成后在 UI 线程上执行。

如果仅当从 UI 线程调用 WaitUntilLoadedAsync 时才想在 UI 线程上执行延续任务(否则在线程池线程上执行),则定义 thread_scheduler 如下:

var thread_scheduler = SynchronizationContext.Current == null
? TaskScheduler.Default
: TaskScheduler.FromCurrentSynchronizationContext();

关于c# - 如何同步运行延续任务?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33512160/

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