你眼中的async await是什麼樣的?

2022-01-13 07:24:53 字數 2913 閱讀 1915

又到了週末的code review環節,這次code review發現了乙個對async/await的理解問題。讓我們直奔主題:

這個理解正確嗎?團隊的爭論焦點在步驟2上,大家錯誤的認為await關鍵字就是等待的意思,為了在第三步拿到結果,執行緒在步驟2處等待直到foodsearchservice返回結果。如果你也是這樣理解的,那麼你應該看看下面的**如何理解?

var foodssearch = new foodsearchservice().searchasync();

var fruitssearch = new fruitsearchservice().searchasync();

var foods = foodssearch.result;

foods.foreach(f => console.writeline("food:", f.name));

console.writeline("done");

剛才錯誤的理解正好是這段**的描述。那麼第一段使用async/await的**如何理解?

使用await標記的方法呼叫(上面例子中的foodssearch)不會阻塞主線程,主線程在步驟2不會等待。

為了說明這個結論,我們用下面的**模擬await(僅僅是模擬其行為,並不能真確執行),我沒有研究過await的實現,但是下面的**跟await具有相同的行為:

var foodssearch = new foodsearchservice().searchasync();

var fruitssearch = new fruitsearchservice().searchasync();

var callback = foodssearch as icallbackregister;

callback.register>(foods =>

", f.name));

console.writeline("done");

}).await(foodssearch);

public class callbackregister:icallbackregister

public void await(task task)

}

從上面模擬的**中我們可以得出兩個結論:

1、沒有任何阻塞主線程的**。

2、盡量推遲await的呼叫,能在步驟2使用await就不要在步驟1使用。因為一旦使用了await,後面所有的**都變成了await所呼叫物件的**,無法跟之前的非同步**並行。即便你在步驟1就使用了await,只能說foodsearchservice和fruitsearchservice兩者不能並行,但是任然不會阻塞主線程——在主線程上永遠沒有等待這一說。

我們再看張圖來解釋一下這期間發生的事情:

設想這樣的**放在乙個gui中button的click事件中,由於await不會阻塞主線程,介面再不會有假死的情況發生。

this.backcolor = color.aquamarine;

this.btnasyncawait.backcolor = color.blue;

var operationa = new longtimeoperationa().getvalueasync();

var operationb = new longtimeoperationb().getvalueasync();

var valuea =await operationa;

text = valuea;

同樣的道理,在web mvc程式設計中,如果controller和ef中全程使用async/await,此時假設使用者有乙個請求過來,iis會從執行緒池中取出乙個執行緒來響應使用者請求,由於主線程沒有任何阻塞,所以iis會很快將執行緒**到了執行緒池中。當ef返回資料並且返回actionresult時,iis再次從執行緒池中拿出乙個執行緒來對使用者請求做響應。所以

正是由於async/await不會阻塞主線程,我們才說async/await會提高iis的響應能力。

另外async/await的使用並不會提公升訪問資料庫的效率,該花多長時間還得花多長時間。最後我們給出task.result版本的click事件,由於呼叫task.result會阻塞主線程,所以你可以看到介面假死的現象。

this.backcolor = color.beige;

this.btntaskresult.backcolor = color.blueviolet;

var operationa=new longtimeoperationa().getvalueasync();

var operationb=new longtimeoperationb().getvalueasync();

var valuea = operationa.result;

text = valuea;

你是誰眼中的風景

卞之琳 斷章 你站在橋上看風景,看風景的人在樓上看你。明月裝飾了你的窗子,你裝飾了別人的夢。很久以前喜歡過乙個女生。我是在一次運動會上偶然看見她的,當時覺得她很漂亮,很溫柔,身上有一種特殊的氣質,這種氣質深深地吸引著我。從那時起我便開始關注她。我從她的朋友那,從她朋友的朋友那裡打聽著她的一切,只要是...

黃聖池《你是我眼中的山川和海洋》

日前,由人氣小生黃聖池主演的電視劇集 你是我眼中的山川和海洋 正在熱播。黃聖池以溫暖清新的學長形象成為全劇焦點,帶來了 借月光 挽髮殺 等高甜劇情。在最新更新的劇集中,借光cp 繼續發糖,黃聖池親身示範完美男友的正確開啟方式,更在女主遭遇挫折時大展男友力,收割少女心。黃聖池撩心名場面不斷 氣球告白打...

我眼中的RestFul API是怎樣的

好久沒寫了,那我就寫著restful先把。首先restful api是一種介面設計規範!然而restful有個很高大上的解釋 表現層狀態轉移。what!這樣誰看得懂 rest全稱是 resource representational state transfer 意思就是資源在網路中以某種表現形式進...