2011-07-16 38 views
3

我使用的ReSharper幫我察覺可能的錯誤在我的代碼,而且,雖然不是一個錯誤,它一直在抱怨,我應該在聲明中使用關鍵字var明確,而不是輸入變量。就個人而言,我覺得它更清楚,我和任何人讀我的代碼,如果我寫ReSharper的和隱式類型的變量

IList<T> someVar = new List<T>(); 

,而不是

var someVar = new List<T>(); 

知道有是兩種方式之間不存在性能差異,應該我忽略這些提示或堅持使用var關鍵字?

難道只有一個口味問題或者是隱式類型變量一個好的做法呢?

+0

[在C#中使用var關鍵字]可能的重複(http://stackoverflow.com/questions/41479/use-of-var-keyword-in-c) – CodesInChaos

+0

絕對是一個品味問題。我喜歡明確。不知道爲什麼Resharper建議你改變。我建議禁用它來保持你的理智。 –

+0

相關:http://stackoverflow.com/questions/1504064/resharper-cleanup-code-vs-var-keyword –

回答

5

我看到至少有兩個原因。

一是DRY principle它的事項:不要重複自己。如果將來你決定改變變量的類型從List<>Stack<>LinkedList<>,然後用var你不得不在一個地方改變,否則你不得不在兩個地方改變。

兩種泛型類型聲明可能相當長。 Dictionary<string, Dictionary<int, List<MyObject>>>有人嗎?這並不適用於簡單的List<T>,但不應該爲不同的對象類型提供兩種代碼樣式。

1

這只是一個更加簡潔的事情,就像汽車的屬性。堅持你最舒適的感覺。

3

這只是一個風格問題。如果右側的類型在您的示例中立即顯而易見,則傾向於使用var,但如果您不喜歡var,則禁用該規則是完全正確的。許多程序員更喜歡明確的輸入。

查看Eric Lippert的博客文章Uses and misuses of implicit typing,詳細瞭解var何時適用。

2

這主要是一種編碼風格的問題(匿名類型除外)。就個人而言,我在編寫代碼時經常使用var,但在完成後使用ReSharper的代碼清理將它們轉換回顯式類型。這使我能夠更快速地編寫代碼,但隨後將代碼轉換爲我自己和其他人更易讀的代碼(畢竟代碼只寫了一次,但多次閱讀)。

我關閉ReSharper的提示使用風險價值「通過關閉下面的「語言機遇設置」(在選項中,代碼檢查,檢查嚴重程度):

使用「變種」關鍵字時,初始化明確聲明類型。
儘可能使用'var'關鍵字。

您可以配置ReSharper的轉換「變種」來顯式類型的代碼清理設置下:

使用「變種」在聲明

2

我只用VAR當類型聲明太長(15+字符)。否則顯式聲明更具可讀性。

要ReSharper的8.2禁用它,去ReSharper的>選項>代碼檢查>檢驗嚴重性>語言用法機會。在搜索框中鍵入單詞「使用」有助於篩選列表。

Reshaper screenshot

1

這是一個初級開發者一個很大的問題。不一定那個提問者是初級的,但是在向一個初級開發者提供信息之前確保澄清是一件好事。

本着這種精神,誰認爲這個問題應該始終明白,可讀性是幾個質量屬性之一,而其中最重要的當然是一個要掌握早期。可讀性包括變量命名實踐和顯式代碼,以命名一對夫婦。可讀性的

這就是說,一個單獨的微方面是是否要經由var關鍵字使用隱式類型。簡短的回答是也許。舉例受過教育的答案可能縮小也許很少

因此,爲了使這個最容易理解的,我要開始的原因經由var關鍵字用含蓄的打字。

(語言透視)不使用隱式類型的第一個原因是因爲C#的主要優點是它是強類型語言。有很多精彩的語言,其優點包括不是強類型,如Javascript。每種語言都有不同,並有其自身的優勢/弱點。對於C#,強類型是其最重要的優勢之一。


這個答案假設你的代碼是SOLID。如果你是在一箇舊的代碼庫工作,或者是誰,還沒有完全實現了完全專注於依賴注入或Liskov替換初級開發人員,那麼微調整你var的使用是不是在您的重點應該是現在。

有隻分配給一個變量的幾種方法。這是我認爲的那些現在:

ISomething someVar = new Concrete(); // <1. Can't use var to create Interfaces. 

var someVar = GetFromMethod(); // <-- 2. Taken from return type 

var someVar = new MyPerson(); // <-- 3. Custom complex reference type 

var someVar = new DateTime(); // <-- 4. Built-in simple Reference Type 
var someVar = string.Empty;  // <--  << 

var someVar = new List<T>();  // <-- 5. Built-in complex Reference Type 
var someVar = new Dictionary<string, Dictionary<int, List<MyObject>>>(); 

var someVar = true;    // <-- 6. simple Value type assignment 

var someVar = 1;     // <-- 7. complex Value type assignment(s) 
var someVar = 1.0;    // <--  << 
var someVar = 1.0d;    // <--  << 

foreach (var i = 0; i <= . . .) // <-- 8. Same as 7 above, but different context. 

var someVar = new {Name = "yo"}; // <-- 9. Instantiate Anonymous Type 

(故障)

在上面的例子例子1,我說明了唯一的一次,你根本不能使用var關鍵字。您顯然不能在接口下創建具體實例。我將更詳細地介紹在#5中使用接口。 不要不能使用VAR這裏

2.例2假定有人使用相同的開發工具,你,和每個人都希望花時間在閱讀代碼,調查該報稅表類型的方法。取決於你閱讀代碼或代碼審查的速度有多快,這可能是一個微不足道的或主要的缺點。不要使用VAR這裏

你爲什麼實例化一個newable在線?正如我剛纔所說,這些例子假定你練習SOLID原則。這種聲明變量的方式會產生代碼異味。如果您搜索代碼庫中的new關鍵字,則唯一的結果應該是自動生成的代碼,合成根目錄或下面的#4。 這裏就不使用VAR永遠做這個

4.new DateTime();,和一對夫婦等珍稀內置簡單類型是一些罕見的時代,你應該看到在你的代碼庫new關鍵字。在示例4中使用var關鍵字並不是什麼大問題。但是,老實說,你在這種情況下爲了隱藏而購買什麼?字符串的同樣問題。 可以在這裏使用var ...但爲什麼?

5.您應該總是嘗試使用最小特定類型。總之,這意味着使用小接口。此規則主要適用於面向外部的API,因爲您希望保持更改儘可能靈活而不會破壞用戶。這條規則不是嚴格適用於內部代碼的唯一原因,因爲如果開發人員想要做出突破性改變,他們有能力花費額外的時間並且做額外的工作來級聯分解修復。這不是一個很好的藉口。

..... 5.1因此,對於第一部分,請注意someVar變成類型Generic.List<T>。如果你想創建一個類型爲IList的變量,正如我所看到的那樣,那麼使用var關鍵字不是你想要的。這通常是用可能的最小特定類型聲明變量的規則。看看:IList vs List。如果你故意不想讓變量的使用包含List<T>中的所有額外垃圾?這些規則是有原因的。 儘量不要使用var關鍵字,如果你可以遵循這個規則。

..... 5.2假設你不關心或不想按照建議使用接口,這很好。這也適用於長度的概念。如果您擁有嵌套級別的集合並且您的聲明很長,則沒有人會因使用var關鍵字而責怪您。 好吧,如果你不使用的接口

這是類似的例子#7,但適用於非數字的值類型。簡單的問題是,「爲什麼?」就像我在#4中所說的那樣,你在買什麼?假設你正在使用默認值,你將不得不指定類型。爲什麼要混合規則,它會買什麼? 當然,但爲什麼?

例如: - 你必須要明確的有時,無論如何,爲什麼規則混合?:

bool isVarOkay, canUseVar; 
char a, b, c, d, e, f; 
bool isSample = true; 
byte etc; 
var isOtherSample = true; //<-- why? 

7.還有一堆數值類型。大多數推理都是爲了精確,有些是爲了語義目的。無論哪種方式,爲什麼讓編譯器猜測你想要什麼而不是明確的。如果有時間是明確的,那麼數值類型就是時間。至於普通ol int去,也許有一些使用var的餘地,因爲它是如此直接和明顯。但我寧願將它保存到第8點。不要使用var關鍵字

此代碼結構在很多地方使用,它看起來幾乎沒事做。但是,再一次:爲什麼,你還在保存什麼? varint都是3個字符。 當然,但爲什麼?

9.在匿名返回的情況下,您幾乎必須使用var關鍵字。沒有這樣做會挫敗Anonymous的目的。大多數匿名類型可以內聯,以便他們的結果立即轉化爲有用的東西,所以他們不一定必須分配給一個變量。但是有一些不值得迴避的場合。 如有必要,請將var用於匿名類型。


結論

var關鍵字是不可避免的匿名類型。另外,對於泛型類型有多種級別的泛型可能會有所幫助,例如Dmitry的例子Dictionary<string, Dictionary<int, List<MyObject>>>。最後,如果您在數字4,5,6和8中顯示的示例中使用var關鍵字,它不會傷害任何人的感情。但是您不會購買任何東西。

使用關鍵字var可以更改類型或允許您堅持DRY原則的想法不過是一個虛假借口罷了。只有在極少數情況下,聲明正確的作業方代表了類型應該是什麼。