[英]C# - transform an async task from one type to another
我習慣於使用 Scala 編程語言 - 使用 Scala 我可以映射期貨,例如:
val response: Future[HttpResponse] = asyncHttpClient.GetRequest("www.google.com")
val statusCode: Future[Int] = response.map(r => r.statusCode)
最近我開始使用 C#,我發現自己處於與上面示例相同的情況,但是我無法弄清楚如何“映射”任務。
這是我想要實現的一個例子:
Task<HttpResponseMessage> response = httpClient.GetAsync("www.google.com")
Task<int> statusCode = response.Map(response => response.StatusCode)
謝謝
對現有方法最直接的翻譯是:
Task<int> statusCode = response.ContinueWith(t => t.Result.StatusCode)
但是在實踐中,您幾乎總是等待任務以獲得結果。 也許你應該看看 async/await。
老實說,我有點驚訝框架中沒有任何內容。 (更有可能的是,有一個我沒見過。)不過你可以很容易地構建它:
public static async Task<TResult> Map<TSource, TResult>
(Task<TSource> task, Func<TSource, TResult> selector)
=> selector(await task.ConfigureAwait(false));
注意:在這里使用ConfigureAwait
並不總是明確的。 您可能希望包含continueOnCapturedContext
參數:
public static async Task<TResult> Map<TSource, TResult>(
Task<TSource> task,
Func<TSource, TResult> selector,
bool continueOnCapturedContext = false) =>
selector(await task.ConfigureAwait(continueOnCapturedContext));
使用現代 C#,這應該用await
重寫:
var response = await httpClient.GetAsync("www.google.com")
var statusCode = response.StatusCode;
這可以與async
一起使用來創建Task<int>
:
async Task<int> Fetch(string url)
{
var response = await httpClient.GetAsync(url);
return response.StatusCode;
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.