非同步編程系列第01章 Async非同步編程簡介

来源:http://www.cnblogs.com/tdws/archive/2016/06/26/5617242.html
-Advertisement-
Play Games

Async in C# 5.0(C#中的非同步編程Async) 蝸牛翻譯之第一章 ...


寫在前面

  在學非同步,有位園友推薦了《async in C#5.0》,沒找到中文版,恰巧也想提高下英文,用我拙劣的英文翻譯一些重要的部分,純屬娛樂,簡單分享,保持學習,謹記謙虛。

  如果你覺得這件事兒沒意義翻譯的又差,盡情的踩吧。如果你覺得值得鼓勵,感謝留下你的贊,祝各位愛技術的園友在今後每一次應該猛烈突破的時候,不選擇知難而退。在每一次應該獨立思考的時候,不選擇隨波逐流,應該全力以赴的時候,不選擇儘力而為,不辜負每一秒存在的意義。

   轉載和爬蟲請註明原文鏈接http://www.cnblogs.com/tdws/p/5617242.html,博客園 蝸牛 2016年6月26日。

目錄

第01章 非同步編程介紹

第02章 為什麼使用非同步編程

第03章 手動編寫非同步代碼

第04章 編寫非同步方法

第05章 Await究竟做了什麼

第06章 以Task為基礎的非同步模式

第07章 非同步代碼的一些工具

第08章 哪個線程在運行你的代碼

第09章 非同步編程中的異常

第10章 並行使用非同步編程

第11章 單元測試你的非同步代碼

第12章 ASP.NET應用中的非同步編程

第13章 WinRT應用中的非同步編程

第14章 編譯器在底層為你的非同步做了什麼

第15章 非同步代碼的性能

第1章 非同步編程介紹    讓我們從C#5.0非同步編程Async和他將對你意味著什麼來開始介紹吧!   非同步編程

   如果我們在一個耗時的操作中使用非同步的代碼,在其執行過程中,我們不需要無謂的等待。這種方式和在耗時操作的整個執行過程中的阻塞型代碼是相對的。

我們所說的耗時操作包括:

·網路請求

·硬碟數據訪問

·延遲一段時間的操作

  全部的區別在於正在運行代碼的線程。在廣泛應用的編程語言當中,你的代碼運行在操作系統的線程中。如果在遇到耗時操作時,你的線程可以繼續去做其他事情,這就是非同步編程。如果你的線程除了等待什麼也不做,那就是同步的或者說是阻塞型代碼。

當然我們還有第三種方式去處理耗時操作—輪詢。這是一種不斷重覆“詢問”耗時操作是否完成的操作。儘管它在處理段時間操作上有自己的地位,但這通常不是一個好的解決方案。

 

  你也許在過去的工作中使用過非同步編程。你可能開啟一個新的線程或者使用線程池,這也是非同步編程,因為你所工作的線程可以不被阻塞地去繼續做其他事情。而你的console app,像Console.ReadLine(),這就是阻塞型,在web app中,如果也是這樣的設計等待用戶輸入,將會是多麼糟糕呀。

  非同步編程中很常見的難點在於這個操作在什麼時候結束,以便於執行下一步的某些操作。但是這在阻塞型代碼中,很容易做到:你只需要在將接下來的代碼寫在耗時操作的下一行就好。如果不加以處理,這種方式在非同步的世界中是怎樣也行不通的。因為幾乎可以確定的是,你下一行代碼是在耗時操作完成之前就已經執行了。

  為瞭解決這個問題,我們發明瞭一些方式,為了在後臺操作完成後去執行下一步操作:

·將下一步操作所需的代碼插在耗時操作代碼主體的後面

·註冊一個當耗時操作結束時會觸發的方法

·在完成後傳遞委托或者Lambad(回調)

  如果你下一個操作需要在特定的線程上執行(例如Winform和WPF的UI線程),你還需要在這個線程上安排隊列排序,這是很複雜的。

  非同步代碼有什麼了不起的?

   非同步編程釋放了它開始的線程,這有許多原因確實不錯。首先,線程占用並且占用很少的資源,通常只用一個線程就可以完成主要的工作,就像UI線程,但是如果你不儘快釋放它,你的app就會出現未響應狀態。我們將會討論更多的原因在下一章。

   最重要的,也是最令我激動的一點是:非同步編程讓我們得以有機會去盡情享受電腦並行計算帶來的好處。非同步編程讓我們以新的並且合理的方式構建應用程式,用更細粒度的並行和無需編寫難以維護的複雜代碼。第十章將會詳細探討此可能性。

  什麼是非同步編程?

   在C#5.0當中,微軟編譯器團隊為我們增加了一個強大的新功能。

   它以兩個新型關鍵字出現:。

·async

·await

   它當然依賴於一些環境,要求你使用.NET FrameWork4.5,才能你的async代碼有用。

Async是屬於C#編譯器的一個功能,不能被封裝到一個類庫,它對你的源代碼進行改造,就像在早期C#版本對Lambda和迭代器所做的事情一樣。

 

   通過免去早期C#版本非同步編程所需的複雜模式和代碼,這個新功能使非同步變得非常簡單。有了這個功能,我們可以合理地用非同步編程的風格編寫整個項目。

   非同步編程一直在C#中是可行的的,它以前涉及編程者大量的手工工作,現在C#的async關鍵出現後,非同步編程的使用變得非常容易。

  非同步編程Async做了什麼?

   Async功能提供了一種讓你表達在耗時操作後需要做什麼事情(執行什麼代碼)的方式,並且它易讀易懂,表現為非同步編程。

   Async方法被編譯器轉化的像你平時所寫的阻塞代碼,這裡有一段簡單的下載網頁的阻塞型代碼:

private void DumpWebPage(string uri)
{
WebClient webClient = new WebClient();
string page = webClient.DownloadString(uri);
Console.WriteLine(page);
}

   這裡還有一段使用Async實現相同功能的代碼:

private asyncvoid DumpWebPageAsync(string uri)
{
WebClient webClient = new WebClient();
string page = awaitwebClient.DownloadStringTaskAsync(uri);
Console.WriteLine(page);
}

   兩段代碼在錶面上看起來是非常相似的,但是在其外表下,有很大的不同。

   被標記為Async的方法,要求方法使用await關鍵字,為了遵循慣例,我們也再方法的尾碼名加上了Async。

   有趣的地方是await關鍵字,當編譯器遇到它時,他將方法分開(chop the method up),事實上它是很複雜的,所以現在我介紹一個我覺得更易於理解的簡單情況的假結構。

1.await後所有的代碼被分離到另一個方法。

2.我們使用一個新版本叫做DownloadStringTaskAsync的DownloadString方法,它做和原版相同的事情,但它是非同步的。

3.這意味著我們可以給它新的第二種方法,即在它完成時它會調用。我們使用一些“魔法”來做這件事,稍後我會告訴你。

4.當下載結束,它將會把我們調用回來帶著已經下載好的可以使用的string字元串,在這種情況下,寫到控制台。

//這就是await分解的方法,上文所說的假的結構(譯者博客園蝸牛註解)
private void DumpWebPageAsync(string uri)
{
WebClient webClient = new WebClient();
webClient.DownloadStringTaskAsync(uri)<- magic(SecondHalf);  //魔力的方法調回來
}
private void SecondHalf(string awaitedResult)
{
string page = awaitedResult;
Console.WriteLine(page);
}

   當它運行此代碼時,調用線程會發生什麼?當線程抵達DownloadStringTaskAsync方法,下載工作開始,但並不在此線程中執行,在這個線程上,我們抵達了方法的結尾或者說是return,這個線程下一步做什麼由我們調用者來決定。如果是UI線程,它將會返回執行用戶操作,除此外,它的資源將會被釋放,這意味著我們在做非同步編程!

  非同步編程並不能解決所有問題

    非同步代碼被微軟編譯器開發團隊儘可能設計的像你常寫的阻塞(同步)代碼,我們可以把耗時操作或者遠程操作處理地像本地操作和快速。但是保持和非同步調用一樣的性能和優勢。

   然而,這樣的設計不是讓你忘記Async是後臺操作還有發生回調。你需要小心很多事情,包括:

·異常和try-catch-finally模塊

·方法的返回值

·線程和上下文

·性能

   如果不瞭解它真正發生了什麼,你的應用程式可能會意想不到的掛掉,並且你將無法理解異常信息和沒有能力去解決問題。

 

寫在最後  

 終於翻譯好了第一章,四頁,花了幾個小時。昨天讀了一遍,沒讀懂,今天翻譯一遍果然收穫頗多。如果您表示支持,給個贊吧!繼續閱讀下一章 我們有什麼理由使用Async非同步編程


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 本寶寶只是一個菜鳥,寫寫學習筆記,以便溫故知新,如果哪裡不對或者不足,望大牛指正。 1.我們先舉個例子說明一下,eg:加減乘除的運算[一步步優化] ⅰ.[第一種寫法] ⅱ.以上的這種寫法,顯得特別不專業,也不美觀,那就優化一下,看看[第二種寫法] ⅲ.以上寫法是不是也有許多不足呢? 業務邏輯層和和客 ...
  • 橋接模式:實現系統可能有多角度分類,每一種分類都有可能的變化,那麼就把這種多角度分離出來讓他們獨立變化,減少它們之間的耦合 下麵的實例是一個手機軟體的實例,對於手機來說,我們可以從手機的品牌進行分類,也可以從軟體角度分類(功能機),同時手機品牌與手機軟體是一個 聚合的關係。 代碼如下: 運行結果: ...
  • ASP.NET MVC5入門基礎,添加一個模型、視圖、控制器,完成增刪改查的功能。 ...
  • 一、前言 上篇運用了.Net Remoting技術解決了本地與伺服器版本對比,並下載更新包的過程。 本篇主要是應用Process,來實現重啟程式的過程。 情景假設: Revit2016正載入某dll,其版本為1.0.0.0。伺服器的更新dll版本為1.0.0.10。 下載完後,Revit2016關閉 ...
  • 寫在前面 在學非同步,有位園友推薦了《async in C#5.0》,沒找到中文版,恰巧也想提高下英文,用我拙劣的英文翻譯一些重要的部分,純屬娛樂,簡單分享,保持學習,謹記謙虛。 如果你覺得這件事兒沒意義翻譯的又差,盡情的踩吧。如果你覺得值得鼓勵,感謝留下你的贊,在今後每一次應該猛烈突破的時候,不選擇 ...
  • 國內知名B2C系統  Urselect 很不錯的asp.net 架構參考與nopCommerce abp等國外開源系統,針對國內定製,採用領域模型設計,不過該系統很適合企業做B2C,品牌電商,商城操作簡單實用,功能也相當強大,是目前.net 系統裡面技術實力較強的後起之秀。 ...
  • 0. 沒有找到一款中意的分頁插件,又不想使用現成的(醜到爆),所以自己動手造一個吧 先看下效果(其實也不咋滴...): 我的小站地址:我的Bootstrap小站; PS:(問博客園:為什麼老是刪我的置頂隨便?上一篇閱讀量都快500了,也分分鐘給我從首頁刪掉...真是無語了<博客園地址:http:// ...
  • 第一次寫,小緊張! 即將畢業了,現在將我畢業設計中用到的小的編程技術以及自己的一些理解分享出來,希望可以做點小貢獻。 首先要感謝網上各路大神無私的分享,沒有你們,就沒有我的收穫。 在大四之前,對於編程只是學習過簡單的C語言,從來沒有接觸過工程實踐。最後的畢業設計肯定要開發程式,於是認真學習了一段時間 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...