在Visual Studio 2012中使用.net 4.0上的Microsoft.Bcl.Async异步

时间:2014-10-13 13:07:59

标签: c# .net visual-studio-2012

尝试在Visual Studio 2012中使用.net 4.0上的Microsoft.Bcl使用Async。结果未显示。

private void button3_Click(object sender, EventArgs e)
        {
            byte[] resultBytes;// = ReceiveStringAsync().Result;
            Task<byte[]>[] tasks = new Task<byte[]>[1];
            tasks[0] = ReceiveStringAsync();
            Task.WaitAll(tasks, -1);
            resultBytes = tasks[0].Result;
            MessageBox.Show("Async Mode called in sync - " + data.Length.ToString());
        }

        public async Task<byte[]> ReceiveStringAsync()
        {
            string strURL = @"https://testurl.com";
            WebClient client = new WebClient();
            byte[] data = await client.DownloadDataTaskAsync(strURL).ConfigureAwait(true);

            return data;
        }

1 个答案:

答案 0 :(得分:1)

这是问题所在,与您使用.NET 4的事实无关:

Task.WaitAll(tasks, -1);

这将阻止tasks中的所有内容完成。此时,您的UI线程无法再执行任何工作了......但做更多工作,以便在ReceiveStringAsync之后恢复await内的代码表达。因此,在Task.WaitAll完成之前,您的任务无法完成,在任务完成之前无法完成,并且您遇到了死锁。

这里的教训是从不在UI线程中使用阻止调用,例如Task.WaitAll(或Task.ResultTask.Wait())。

解决方案是同时使button3_Click异步,因此await可以Task<byte[]> ReceiveStringAsync发送private async void button3_Click(object sender, EventArgs e) { byte[] resultBytes = await ReceiveStringAsync(); // Not clear what data is here, but that's a different matter... MessageBox.Show("Async Mode called in sync - " + data.Length.ToString()); }

ReceiveStringAsync

顺便说一句,Task<byte[]>方法返回Task<string>而不是{{1}} ... 真的奇怪