我一直在閱讀,我注意到當 Async/Await 在 I/O 或任何其他硬體組件上運行時,它不一定會創建一個新執行緒。
但是當操作是 CPU Bound 時會發生什么?
public partial class Form1 : Form
{
private static List<string> _logs = new List<string>();
public Form1()
{
Print("Form constructor");
InitializeComponent();
}
private async void button1_Click(object sender, EventArgs e)
{
Print("Caller");
await SomeLongOperation();
}
private async Task SomeLongOperation()
{
Print("Called");
await Task.Delay(10000);
Print("Called after task");
}
public void Print(string txt)
{
_logs.Add($"I'm writing from thread {Thread.CurrentThread.ManagedThreadId}. And, {txt}");
}
}
假設我有這個類,如果主執行緒呼叫button1_Click方法運行到awaitable,然后剩下的方法在訊息回圈中排隊,從而讓主執行緒繼續作業,那么誰在運行等待,因為主執行緒已經在 UI 上作業并等待等待完成。
uj5u.com熱心網友回復:
我認為您將“異步”與“并行”混淆了。
- 異步意味著執行緒在等待其他事情時被釋放以做其他事情。這是關于你的代碼如何等待。
- 并行是指代碼的兩個部分同時運行。這只能用多個執行緒來完成。這是關于您的代碼如何運行的。
您的示例代碼是異步的,但不是并行的。一切都在一個執行緒上完成。Task.Delay不是 CPU 操作。執行緒無事可做。沒有執行緒。
如果您確實有一些 CPU 密集型操作要運行,則可以使用Task.Run. 例如:
await Task.Run(() => DoSomethingIntensive());
這混合了異步和并行的想法。DoSomethingIntensive()在單獨的執行緒上運行。那是平行的。但是主執行緒異步等待,這意味著它可以自由地去做其他事情(例如回應用戶輸入),同時等待另一個執行緒做它的事情。
uj5u.com熱心網友回復:
在async和await關鍵字實際上并沒有引起執行緒還創建。異步方法不需要多執行緒,因為異步方法不在其自己的執行緒上運行。該方法實際上在當前同步背景關系上運行,并且僅在該方法處于活動狀態時才使用執行緒上的時間。開發人員可以使用Task.Run將受 CPU 限制的作業任務移動到后臺執行緒。話雖如此,后臺執行緒對只是等待結果可用的行程沒有幫助。
async/await可以在此處找到有關執行緒的更多資訊- https://docs.microsoft.com/en-us/aspnet/core/web-api/?view=aspnetcore-2.2#automatic-http-400-responses -
轉載請註明出處,本文鏈接:https://www.uj5u.com/yidong/398771.html
