2013-08-05 54 views
20

Tôi có đoạn code sau đâyBắt giá trị trả về từ Task.Run

public static async Task<string> Start(IProgress<ProcessTaskAsyncExProgress> progress) 
    { 
     const int total = 10; 
     for (var i = 0; i <= total; i++) 
     { 
      await Task.Run(() => RunLongTask(i.ToString(CultureInfo.InvariantCulture))); 
      if (progress != null) 
      { 
       var args = new ProcessTaskAsyncExProgress 
       { 
        ProgressPercentage = (int)(i/(double)total * 100.0), 
        Text = "processing " + i 
       }; 
       progress.Report(args); 
      } 
     } 
     return "Done"; 
    } 

    private static string RunLongTask(string taskName) 
    { 
     Task.Delay(300); 
     return taskName + "Completed!"; 
    } 

Trong dòng này:

await Task.Run(() => RunLongTask(i.ToString(CultureInfo.InvariantCulture))); 

Làm thế nào để lấy lại giá trị chuỗi của RunLongTask?

Tôi đã thử

var val = await Task.Run(() => RunLongTask(i.ToString(CultureInfo.InvariantCulture))).Result; 

Nhưng tôi nhận được một lỗi "chuỗi là không awaitable"

Trả lời

51

Tháo Result từ kết thúc. Khi bạn await bạn sẽ nhận được Result trở lại từ phương pháp chờ đợi.

var val = await Task.Run(() => RunLongTask(i.ToString(CultureInfo.InvariantCulture))); 
5

Đây không phải là một câu trả lời trực tiếp cho câu hỏi cũ, nhưng đối với những người khác tìm kiếm:

"Thông thường" bạn không nên làm điều này, nhưng đôi khi bạn cần phải phù hợp với một API thư viện để bạn có thể sử dụng một hàm wrapper như dưới đây:

private async Task<string> WrapSomeMethod(string someParam) 
{ 
    //adding .ConfigureAwait(false) may NOT be what you want but google it. 
    return await Task.Run(() => SomeObj.SomeMethodAsync(someParam)).ConfigureAwait(false); 
} 

Và rồi gọi đó là thay vì với .Result như dưới đây:

string blah = WrapSomeMethod(someParam).Result;