第一個就是異步方法,async-await,所謂async關鍵字,並沒有什么實際上的語法意義,只是寫在函數簽名的位置讓編譯器方便進行查找以及靜態檢查,並且提醒程序員這是一個異步方法而已。至於await,這是一個運算符,作為一個語法糖,編譯器在背后替你展開了所有的代碼。略去了這部分細節,可以像寫同步調用一樣寫異步調用。
await一個表達式,空值列會在執行到這個表達式時立即返回,同時這個表達式在另一條線程中繼續執行,返回的控制流可以繼續去處理其他的一些事情,比如UI的刷新和相應什么的,這樣就不會在執行一個高耗時的操作時卡住整個界面。當異步操作結束后,控制流會從剛才返回的地方恢復上下文,然后從中斷的地方進行后續的操作。
一個異步的調用返回一個Task,Task<T>,void,或者其他的IOperation什么的,表示一個正在進行的異步操作,await這個操作,不嚴謹的說就是讓這個操作進行到出結果,然后得到的就是這個操作的結果,可能是void,也可能是一個返回值。
實際上await 異步方法就是await 異步方法的返回值,也就是暫時地退出當前調用異步方法的方法,干一些別的事前,然后在異步方法結束后再回來繼剛才的事情,有這么一個比喻:你打電話叫了外賣,你不是一直站在門口等外賣小哥來,而是先去干些別的事情,等外賣小哥來了之后,你去拿外賣,然后繼續你點外賣的目的:吃飯。
以上過程寫成表達式就是
var 食物 = await 叫外賣(); 吃(食物);
在await叫外賣后,控制流返回,一般是回到消息循環或者事件循環里干別的事,然后外賣到了,吃,然后繼續別的事情。
微軟已經在C++的新提案中建議async-await關鍵字了,自己也已經在VS2015中進行了實現,我還沒有試過C++的異步調用,下一個階段的技術探索就是這個吧:多線程操作以及異步的后台實現。
第二個是數據綁定,總之實現方式就是在數據被修改的時候觸發一個OnValueChanged回調,這個回調又觸發一個事件,事件的處理函數(由編譯器生成),修改與之綁定的控件的值,還有一個值得一提的是轉換器,轉換器的實現是通過實現一個接口IValueConverter,讓編譯器生成的代碼能夠把源數據用ValueConverter處理成目標數據,隨后更新控件的值。沒有Converter的時候相當於調用對象本身的ToString方法,把對象轉成字符串,輸出到界面上去(當然這是針對字符串的綁定)。
為什么只能在UI線程里面操縱UI呢,等我理解了多線程再說吧。