c# - 在异步库方法中处理共享成员变量的推荐做法是什么?
问题描述
在阅读了几篇关于 async await 的文章后,我现在明白了以下内容:
- 作为库作者,您应该始终避免对应用程序正在使用的
.ConfigureAwait(false)
做出假设SynchronizationContext
- 的效果
ConfigureAwait(false)
是它将使用线程池上下文,这意味着该方法的其余部分可以在任何空闲线程中运行 - 您不能在
lock
块的主体中使用 await
假设您正在创建一个库,该库在非静态类上具有异步 API 方法,并且该类具有一些跨其 API 方法共享的成员变量。您如何编写这些方法以确保以线程安全的方式访问成员变量?
解决方案
根据您的需要,您可以async
使用其他BCL 同步原语控制方法中的并发性
其中最简单的可能是SemaphoreSlim
Semaphore 和 SemaphoreSlim 类
和类限制可以
System.Threading.Semaphore
同时System.Threading.SemaphoreSlim
访问共享资源或资源池的线程数。请求资源的其他线程等待直到任何线程释放信号量。因为信号量没有线程亲和性,所以一个线程可以获取该信号量,另一个线程可以释放它。SemaphoreSlim 是 Semaphore 的轻量级替代方案,只能用于单个进程边界内的同步。
例子
private SemaphoreSlim _sync = new SemaphoreSlim(1,1);
...
public async Task SomeMethodThatAccessSharedResources()
{
await _sync.WaitAsync();
try
{
// example of async call
await Task.Delay(1000);
}
finally
{
_sync.Release();
}
}
推荐阅读
- c# - 并排显示图像的一半 - OpenGL
- jqxgrid - 我在使用激活列排序和分组的 jqxgrid 时遇到键盘导航问题
- javascript - 某些更新后,Firefox 中的文本框无法 CTRL + V(粘贴)
- react-native - 拒绝时如何停止 Promise.all 循环
- spring - Spring Boot 不生成表模式
- html - 如何以角度实现带有.xml扩展名的openfile?
- python - 如何构建主页 URL 以使用 Django 呈现 DetailView?
- scala - 理解 Scala 默认参数消息
- regex - 用另一个字符串替换字符串的正则表达式
- xamarin.forms - 以 Xamarin 形式打印 PDF 第一页 UWP 跨平台(桌面)