0
点赞
收藏
分享

微信扫一扫

C# 同步转异步 AutoResetEvent

西特张 2022-10-05 阅读 164

当我们的程序运行时,调用了一段异步的逻辑A,这段异步的逻辑无法转化为同步(如动画、下载进度等)

而,我们又需要等待异步逻辑A处理完成,然后再执行其它逻辑B。

AutoResetEvent 同步转异步

AutoResetEvent autoResetEvent = new AutoResetEvent(false)

AutoResetEvent 可以在线程间发送信号互相通信,通过调用 AWaitOne 来等待信号,调用Set发送信息来启动已等待的线程。

很简单:一个await ,另一个set来唤醒。

  1. AutoResetEvent autoResetEvent = new AutoResetEvent(false)--参数bool:若要将初始状态设置为终止,则为 true;若要将初始状态设置为非终止,则为 false
  2. await Task.Run(() => { autoResetEvent.WaitOne(); });
  3. autoResetEvent.Set();

比如:

private async Task SetDelegateProgress()
{
var delegateProgress = new UIDelegateProgress();
delegateProgress.ProgressCompleted += () =>
{
autoResetEvent.Set();
};
DelegateProgress = delegateProgress;
await Task.Run(() => { autoResetEvent.WaitOne(); });
}

如上案例,当delegateProgress执行完后,通过AutoResetEvent 的方法Set来发送信息来唤醒子线程。

再如动画的同步等待处理:

1 /// <summary>
2 /// 执行动画
3 /// </summary>
4 /// <param name="storyboard"></param>
5 /// <returns></returns>
6 public static async Task ExecuteStoryboradAsync([NotNull] Storyboard storyboard)
7 {
8 if (storyboard == null) throw new ArgumentNullException(nameof(storyboard));
9
10 AutoResetEvent autoResetEvent = new AutoResetEvent(false);
11
12 storyboard.Completed += OnStoryboardCompleted;
13 storyboard.Begin();
14
15 void OnStoryboardCompleted(object sender, EventArgs e)
16 {
17 storyboard.Completed -= OnStoryboardCompleted;
18 autoResetEvent.Set();
19 }
20
21 await Task.Run(() => { autoResetEvent.WaitOne(); });
22

值得注意的是,WaitOne只能在子线程,如果放在主线程的话,会将整个线程终止(例如界面或者其它后台逻辑)

 

AutoResetEvent 可以在多个线程使用WaitOne来暂停线程,而暂停的线程则需要多次set来开启暂停的线程。

给你AutoResetEvent 类似的,还有一个ManualResetEvent。ManualResetEvent 是多个暂停线程,可以通过一次set直接开启全部暂停的线程。

ManualResetEvent与AutoResetEvent 不同的还有Reset方法,Reset与Set相反,为主动暂停线程。


 

缺陷

使用AutoResetEvent的确可以由同步转成异步方法,但是以上方案是创建了一个新的任务,如果是大量的处理会有性能问题~

关键字:动画同步,AutoResetEvent

 

参考资料:

  • ​​Async/Await异步编程中的最佳做法​​
  • ​​使用任务简化异步编程​​

同步转异步

  • ​​C# 同步转异步 TaskCompletionSource ​​
  • ​​C# 同步转异步 AutoResetEvent​​

异步转同步

  • ​​C# 异步转同步 PushFrame​​
  • ​​C# 异步转同步 TaskCompletionSource​​

死锁

  • ​​C# 死锁 Task/AutoResetEvent​​
  • ​​C# 死锁 TaskCompletionSource​​

作者:​​唐宋元明清2188​​

举报

相关推荐

0 条评论