国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 編程 > C# > 正文

C#特性之匿名方法和Lambda表達(dá)式

2019-10-29 21:47:44
字體:
供稿:網(wǎng)友
這篇文章主要介紹了C#特性之匿名方法和Lambda表達(dá)式,需要的朋友可以參考下
 

在我們程序中,經(jīng)常有這樣一些需求:

1.       需要一個(gè)臨時(shí)方法,這個(gè)方法只會(huì)使用一次,或者使用的很少。
2.       這個(gè)方法的方法體很短,以至于比方法聲明都短,寫起來實(shí)在沒勁(我將其稱之為“一句話方法”)。

沒辦法,這樣的方法寫起來真是吃力不討好,比如一些按鈕事件處理中,有些按鈕點(diǎn)擊就是彈出一個(gè)對(duì)話框,或者調(diào)用一下別的什么方法。比如下面的代碼:

 

復(fù)制代碼代碼如下:

this.btnRefresh.Click += new System.EventHandler(this.btnRefresh_Click);
private void btnRefresh_Click(object sender, EventArgs e)
{
    BindData();
}

 

這個(gè)”Refresh”按鈕就是做一下調(diào)用一下BindData()數(shù)據(jù)綁定的方法,為此我們不得不寫一個(gè)新方法。好了,C# 2.0為我們提供了匿名方法:

this.btnRefresh.Click += delegate(object sender, EventArgs e) { BindData(); };

沒勁的代碼沒了。想知道這種寫法的幕后黑手么?
其實(shí)編譯器還是在我們的后面干了一件齷齪的事情:它為我們產(chǎn)生了一個(gè)新的方法,它只是表面上為我們節(jié)省了代碼。

 

復(fù)制代碼代碼如下:

privatevoid<Test>b__0(object sender, EventArgs e)
{
    this.BindData();
}

 

看看這個(gè)編譯器產(chǎn)生的方法的名稱:

<Test>b_0,Test是這個(gè)匿名方法所放置的地方(因?yàn)檫@個(gè)按鈕的時(shí)間我是放在一個(gè)Test方法里的)
還有一點(diǎn)需要注意的是,如果這個(gè)匿名方法是在實(shí)例方法里使用,那么編譯器為我們生成的幕后方法也是實(shí)例方法,否則就是靜態(tài)方法了.
是不是覺得匿名方法這東西很不錯(cuò),減少了很多代碼阿,但是匿名方法的使用還并不人性化,什么是人性化呢?比如你可以用自然的語言將程序代碼讀出來,這樣才算人性化了.在.net 2.0中System.Collections.Generic命名空間下List<T>里有一些新增的方法。比如Find,如果使用匿名方法我們?nèi)绾握{(diào)用呢:

 

復(fù)制代碼代碼如下:

books.Find(delegate(Book book){return book.Price < 50;});

 

代碼是很簡單,但是卻無法朗讀出來,來看看Lambda表達(dá)式的寫法:
books.Find(book=>book.Price<50);這個(gè)Lambda表達(dá)式就可以這樣閱讀出來了:給你一本書,如果它的價(jià)格小于50則返回true。
好了,那我們就走進(jìn)Lambda表達(dá)式吧:

C#特性之匿名方法和Lambda表達(dá)式

將使用了Lambda表達(dá)式的程序集反編譯后,我們發(fā)現(xiàn),它實(shí)際上和匿名方法沒有什么不同。Lambda的輸入?yún)?shù)就對(duì)應(yīng)著delegate括號(hào)里面的參數(shù),由于Lambda表達(dá)式可以推斷參數(shù)的類型,所以這里的參數(shù)無需聲明。Lambda操作符讀作”Goes to”,它后面緊跟著表達(dá)式或者是語句塊(這點(diǎn)和匿名方法也不同,匿名方法只能使用語句塊而不能使用表達(dá)式),下面我就用實(shí)例來說明一下有那些類型的Lambda表達(dá)式:

//x的類型省略了,編譯器可以根據(jù)上下文推斷出來,后面跟著的是表達(dá)式
x => x+1 
deleage(int x){return x+1;}
//后面跟著的是語句塊
x=>{return x+1;} 
delegate(int x){return x+1;}
//輸入?yún)?shù)也可以帶類型,帶類型后別忘記小括號(hào)哦
(int x) => x+1 
delegate(int x){return x+1;}
//也可以多個(gè)輸入?yún)?shù),逗號(hào)分隔,別忘記小括號(hào)
(x,y) => x+y 
delegate(int x,int y){return x+y;}
//無參的也行

() => 1

delegate(){return 1;}

對(duì)于Lambda表達(dá)式來說她的用法就是如此,但是在Lambda背后卻有很多的故事和玄機(jī)。用Lambda表達(dá)式可以構(gòu)建表達(dá)式樹,而表達(dá)式樹對(duì)于Linq來說就像樹根對(duì)于樹一樣重要。在這里就不討論表達(dá)式樹的問題了,這個(gè)東西也不是三言兩語能夠說清楚的,等待時(shí)機(jī)成熟的時(shí)候我們?cè)賮磉M(jìn)一步討論。

Lambda表達(dá)式更多閱讀

Lambda實(shí)際上源遠(yuǎn)流長,我們現(xiàn)在使用的機(jī)器都是馮-諾依曼體系的,屬于圖靈機(jī),在那之前還有一種稱作λ演算的理論,但是圖靈機(jī)由于先被實(shí)現(xiàn)出來,所以大行其道,λ演算后來成就了函數(shù)式編程語言特別是Lisp,在函數(shù)式編程語言里函數(shù)是第一等元素,函數(shù)的參數(shù),函數(shù)的返回值都是函數(shù),程序沒有變量,函數(shù)嵌套函數(shù)。而且函數(shù)式編程語言一直存在于象牙塔中,所以在工業(yè)界并沒有得到通用,不過近年來工業(yè)界比較喜歡“復(fù)古”風(fēng)格,所以函數(shù)式編程語言也慢慢的走上了歷史的舞臺(tái)。函數(shù)式編程能解決一些命令式編程難以解決的問題(或者解決起來非常麻煩)。C#要做到函數(shù)風(fēng)格編程怎么辦?靠原來的方法定義的方式肯定是不可行的,2.0的匿名方法從某種程序上來說解決了這個(gè)問題,但還是不夠,3.0里的Lambda終于很好的解決了,一個(gè)Lambda就是一個(gè)delegate,一個(gè)delegate指向一個(gè)方法,現(xiàn)在我們使用Lambda也能簡單的將方法作為參數(shù)傳遞了,還可以層層嵌套,都是很簡單的事情了。


發(fā)表評(píng)論 共有條評(píng)論
用戶名: 密碼:
驗(yàn)證碼: 匿名發(fā)表
主站蜘蛛池模板: 台湾省| 城固县| 库伦旗| 美姑县| 江孜县| 泽库县| 确山县| 平乐县| 金坛市| 濮阳县| 长宁区| 大英县| 甘孜| 龙胜| 和平区| 高阳县| 体育| 易门县| 吉水县| 登封市| 井陉县| 永嘉县| 霍林郭勒市| 乳山市| 土默特左旗| 华池县| 黑河市| 长岭县| 广宁县| 福泉市| 七台河市| 建宁县| 大新县| 霞浦县| 任丘市| 绥中县| 武陟县| 平江县| 黄陵县| 上虞市| 永定县|