在本篇中我要介紹兩個概念
我覺得這兩個東西必須一起來介紹
這樣才能連貫
C# 裡我們已經匿名方法了現在類型也玩起匿名來了怪不得大家舉報的時候都喜歡匿名為啥?因為匿名被舉報人就找不著報復對象了呗是的匿名就是把名字隱藏起來沒有名字誰還能找得到你啊
匿名類型
在C#裡有這樣一些類型它是作為臨時儲存數據的生命周期只在這個方法內方法結束了這個類型的生命周期也沒有了那麼這裡我們就可以使用一個匿名類型
varKeyPair=new{Key=yuyiValue=};
這個KeyPair就是一個匿名類型注意KeyPair這裡是一個變量名並不是類的名字嗯前面還有一個var這又是什麼呢?這是C# 裡面的隱式局部變量
隱式類型局部變量
還是先介紹一下隱式類型局部變量吧
在C# 裡多了一個關鍵字var他表示這樣的一種類型C#編譯器可以根據上下文推斷的出來比如var I = ;編譯器可以根據後面的賦值推斷的出來i應該是個整型既然是局部變量那麼它就只能用在方法內部了注意C#是強類型的引入了一個var並不是像javascript那樣變成了一個弱類型的語言在編譯器第一次編譯後var就會被確定的類型所替代的所以對於隱式類型局部變量要注意以下幾點
它只能存在於方法內部
它不是一個新的類型只是一個關鍵字或者叫做一個占位符在C#編譯器編譯後它就會被確定的類型所替代
它是編譯器根據上下文推斷出來的所以所有一切不能被編譯器推斷出來的用法都是錯誤的比如不能這樣使用var nullValue = null;因為null啥也不是他是一個空指針是一個不確定的東西也不能這樣使用var I = ;I = abc;編譯器根據第一個賦值會推斷出它是一個整型但是隨後又將一個字符串賦值給它這是怎麼回事呢?
對於var我的建議是不到逼不得已的時候不用那什麼是逼不得已呢?來看我們的匿名類型吧
回到匿名類型
剛才說了匿名類型是沒有名字的類型沒有名字你怎麼來稱呼它怎麼來聲明它?但是匿名類型真的是沒有名字的麼?
看看C#編譯器又在我們背後干了些什麼
使用ILDASM打開編譯過的程序集發現多了一個類型
<>f__AnonymousType<<Key>j__TPar<Value>j__TPar>
這個類型是直接繼承自SystemObject的並且是internal seald(只在程序集內可見並且不能被繼承)有心的你也許會發現這個類型還是一個泛型類型那麼只要我們在使用一個匿名類型的時候參數個數參數名稱不發生變化編譯器是不會為我們產生更多的類型的
varKeyPair=new{Key=yuyiValue=Programer};
varKeyPair=new{Key=yValue=};
varKeyPair=new{Key=Value=abc};
上面三個匿名類型編譯器只會為我們在背後產生一個新類型一個泛型的新類型如果我們將這個匿名類型內的屬性名修改一下對
varKeyPair=new{Key=yuyiValue=Programer};
varKeyPair=new{Key=yValue=};
就會產生兩個新泛型了
<>f__AnonymousType<<Key>j__TPar<Value>j__TPar>
<>f__AnonymousType<<Key>j__TPar<Value>j__TPar>
看看這個命名還是有規律可循哦如果你給這個匿名類型添加一個新屬性呢?這樣又產生了一個新類型了
<>f__AnonymousType<<Key>j__TPar<Value>j__TPar<Test>j__TPar>
嗯這個問題還是值得關注的所以我們在使用匿名類型的時候應該盡量保持一致性
屬性個數一致(這個盡量了)
屬性名稱一致這個比較好把握
只要保持了這個一致性編譯器會為一致的產生同一個類型而不一致的會新產生一個類型如果不一致的太多我想是不是會產生代碼爆炸而致使WorkSet過大造成性能的損失?這個只是我個人認為沒有經過測試
繼續隱式類型局部變量
由於匿名類型在我們編寫代碼的時候並不存在所以匿名類型也不能作為方法的返回值和參數了var一樣也是只能在方法內部使用現在是不是有點明白什麼時候才是逼不得已使用var啊?就是在使用匿名類型的時候匿名類型編譯器可以推斷出來但是靠人工又無法推斷了所以我覺得只在編譯器可推斷而人不可推斷的時候才使用隱式類型局部變量靠我們人工可以推斷的還是不建議使用顯式的聲明變量類型可以增強代碼的可讀性這是一個好的編程習慣不要因為C# 提供了這樣的特性就大用而特用
From:http://tw.wingwit.com/Article/program/net/201311/12067.html