解決非同步檔案 I/O 操作中的 UI 執行緒阻塞
GUI 應用程式中非同步程式設計的目標是防止 UI 執行緒阻塞,確保回應靈敏的使用者體驗。 然而,在 .NET Core 3.1 及更早版本中,非同步檔案系統 API 並不總是遵循最佳實務。
具體來說,File.ReadAllLinesAsync()
可能會阻塞 UI 線程,儘管它是非同步設計的。這是因為該方法沒有完全遵循建議的非同步模式:返回任務之前最少的同步工作。
要在舊版 .NET 版本中規避此問題,請避免直接在 GUI 應用程式中使用非同步檔案系統 API。相反,將同步 API 封裝在 Task.Run()
中。 例如:
<code class="language-csharp">var lines = await Task.Run(() => File.ReadAllLines(@"D:\temp.txt"));</code>
性能觀察:
測試揭示了File.ReadAllLinesAsync()
的阻塞行為。 在舊版 .NET 版本中,在傳回未完成的任務之前,在 SSD 上處理 6MB 檔案會導致 UI 執行緒阻塞 450 毫秒。
.NET 6 改善:
.NET 6 對非同步檔案系統 API 進行了改進,將阻塞時間顯著縮短至約 19 毫秒。 然而,這些非同步 API 仍然比同步 API 慢(大約是速度的兩倍),而且不是完全非同步的。 因此,使用 Task.Run()
中包含的同步 API 仍然是獲得最佳效能和 UI 回應能力的建議方法。
以上是為什麼非同步檔案 I/O 操作仍然阻塞 .NET 中的 UI 執行緒(以及如何修復它)?的詳細內容。更多資訊請關注PHP中文網其他相關文章!