나는 현재 "Concurrency in C #Cookbook"을 Stephen Cleary가 읽고 있는데, 나는 다음과 같은 기술을 발견했다 :
var completedTask = await Task.WhenAny(downloadTask, timeoutTask);
if (completedTask == timeoutTask)
return null;
return await downloadTask;
downloadTaskhttpclient.GetStringAsync에 대한 호출이며timeoutTaskTask.Delay를 실행 중입니다.
시간 초과되지 않은 경우 downloadTask가 이미 완료되었습니다. 작업이 이미 완료되었다는 것을 감안할 때 downloadTask.Result를 반환하는 대신 두 번째 기다리는 것이 필요한 이유는 무엇입니까?
이미 몇 가지 좋은 해답 / 코멘트가 있지만 여기에 나와 있습니다.
내가 좋아하는 이유는 두 가지가있다.await
위에Result
(또는Wait
). 첫 번째는 오류 처리가 다르다는 것입니다.await
예외를AggregateException
. 이상적으로 비동기 코드는AggregateException
전혀 그렇지 않다면~ 싶다에.
두 번째 이유는 좀 더 미묘합니다. 내 블로그 (및 책)에서 설명 할 때,Result
/Wait
교착 상태를 일으킬 수있다., 및에 사용될 때 더욱 세심한 교착 상태를 야기 할 수있다.async
방법. 코드를 통해 읽고있을 때Result
또는Wait
그것은 즉각적인 경고 플래그입니다. 그만큼Result
/Wait
네가 괜찮다면절대적으로 확실한작업이 이미 완료되었음을 나타냅니다. 이 기능은 한눈에 (실제 코드에서) 볼 수있을뿐만 아니라 변경 내용을 코드화하는 것이 더 쉽습니다.
그 말은 아니야.Result
/Wait
할까요못사용하십시오. 내 지침에 따라 다음 지침을 따르십시오.
await
.Result
/Wait
코드가 실제로 그것을 요구하면. 이러한 사용에는 주석이 있어야합니다.Result
과Wait
.여기서 (1)은 일반적인 경우이므로 사용하려는 경향이 있음을 주목하십시오.await
모든 경우를 다루고 다른 경우를 일반적인 규칙의 예외로 취급합니다.
await
그AggregateException
싸개.AggregateException
비동기 프로그래밍이 아닌 병렬 프로그래밍 용으로 설계되었습니다. - Stephen ClearyWait
에 가입했다.동적 작업 병렬 처리
Task
인스턴스. 그것을 사용하여 비동기 대기Task
인스턴스는 위험합니다. Microsoft는 새로운 " 약속 " 유형을 선택했으나 기존의Task
대신; 기존의 재사용의 단점Task
비동기 작업의 유형은 비동기 코드에서 단순히 사용하면 안되는 여러 API로 끝나는 것입니다. - Stephen Cleary
이것은timeoutTask
~의 제품입니다.Task.Delay
나는이 책에 나오는 것을 믿는다.
Task.WhenAny
보고Task<Task>
내부 작업은 인수로 전달한 작업 중 하나입니다. 다음과 같이 다시 쓸 수 있습니다 :
Task<Task> anyTask = Task.WhenAny(downloadTask, timeoutTask);
await anyTask;
if (anyTask.Result == timeoutTask)
return null;
return downloadTask.Result;
두 경우 모두에서downloadTask
이미 완료되었습니다. 거기에는 아주 작은 차이가 있습니다.return await downloadTask
과return downloadTask.Result
. 후자가AggregateException
코멘트에서 @KirillShlenskiy에 의해 지적 된 바와 같이 어떤 원래의 예외를 감싸고있다. 전자는 원래의 예외를 다시 던질뿐입니다.
두 경우 모두 예외를 처리 할 때마다 다음을 확인해야합니다.AggregateException
오류의 원인을 알기 위해 어쨌든 내부 예외가 발생합니다.
downloadTask
과timeoutTask
? 걔들 뭐해? - Mike PerrenoudAggregateException
와Result
을 통해 첫 번째 예외 대ExceptionDispatchInfo
와await
). Stephen Toub " Task Exception Handling in .NET 4.5 "에서 자세히 논의 됨 :blogs.msdn.com/b/pfxteam/archive/2011/09/28/…) - Kirill Shlenskiy