因此,我正在编写一个客户端API PCL(.NET 4.5,SL 5,Win8,WP8.1,WP SL 8)库,并且我决定一次只允许一个HTTP请求。目前,我使用TPL来执行这些操作:
Task.Factory.FromAsync<Stream>(httpReq.BeginGetRequestStream, httpReq.EndGetRequestStream, null).ContinueWith<Task<WebResponse>>((requestStreamTask) =>
{
return Task<WebResponse>.Factory.FromAsync(httpReq.BeginGetResponse, httpReq.EndGetResponse, null);
}).Unwrap().ContinueWith<HttpWebResponse>((getResponseTask) =>
{
return (HttpWebResponse)getResponseTask.Result;
});
因此,我想添加锁定以防止一次发出多个请求。我知道我可以Monitor.Enter
在开始之前先打电话Monitor.Exit
,然后在最后一次打电话ContinueWith
。但是基于迁移到TPL的锁定Monitor
,由于线程问题,我不能那样使用。我使用该帖子建议的其他阻塞对象没有问题,但据我所知,在PCL中,我唯一可用的锁是Monitor。
所以我该怎么做?
编辑:在下面与Yuval Itzchakov交谈之后,我意识到我只有Monitor
同步类的原因是因为我在PCL中具有Silverlight 5支持。如果没有其他方法,我将考虑放弃对SL5的支持,但我宁愿不这样做。
EDIT2:弄乱之后,我意识到我确实有这个ManualResetEvent
课,我可以使用那个课吗?
由于您正在编写PCL并包括一些较旧的平台(特别是SL5),因此您的选择有些局限。SL5不支持TPL Dataflow,也不是SemaphoreSlim
。
但是HttpClient
是,/也是如此async
await
。这些使您的代码比Task.Factory.FromAsync
+ Unwrap
+干净得多ContinueWith
。
对于可移植async
的同步和/或生产者/消费者队列,我建议使用自己的AsyncEx库。在这种情况下,一个AsyncLock
就足够了;它可以类似于以下方式使用SemaphoreSlim
:
private readonly HttpClient _client = new HttpClient();
private readonly AsyncLock _mutex = new AsyncLock();
public async Task<string> GetStringAsync(string url)
{
using (await _mutex.LockAsync())
{
return await _client.GetStringAsync(url);
}
}
本文收集自互联网,转载请注明来源。
如有侵权,请联系[email protected] 删除。
我来说两句