2009-08-11 8 views
5

存在する場合、この例を取る:上記の例でVarのキーワード型推論曖昧インタフェースおよび実装の両方が

interface IEntity { 
    string Name { get; set; } 
} 

class Product : IEntity { 
    public string Name { get; set; } 
    public int Count { get; set; } // added member 
} 

class Client { 
    void Process() { 
     var product = new Product(); 
     int count = product.Count; // this is valid    

    } 
} 

を、製品の種類は何ですか? IEntityまたはProductですか?製品は具体的な実装(製品)のタイプであると思われます。そのような場合は、特別な状況でのみvarを使用するべきではありません。しかし、resharperのようなツールは、デフォルトでvarを使うことをお勧めします。 1つのインターフェースにプログラムするべきではありませんか?

答えて

1

var product = new Product()は、Productです。そのインターフェイスの外部にメンバーを使用していない場合は、インターフェイスにプログラムすることができます(Product.CountIEntityインターフェイスにありません)。

を追加しました:

また、VS2008で、あなたは暗黙の種類を確認する宣言でvarキーワード上にカーソルを移動することができます。このホバー/ツールチップメッセージは、宣言行の後の変数名でも機能します。 (C# In Depth、211ページ)

+0

ポイントは、変数 "product"は常に "Product" varを使用する場合、実装されたクラス(Product)に余分なメンバがあるかどうか。 – Mank

+0

'Product'が追加するメンバーを含む' IProduct'インターフェースを作ることができます。 – ironsam

0

この場合、varを使用すると、タイプはProductになります。私はデフォルトでvarを使用するのが好きではありません。なぜなら、これは時には少し混乱するコードを読むことができるからです。

私はvarをほとんどLINQクエリで使用することをお勧めしますが、他の場所(例のような)で過度に使用しないでください。 IntellisenseでIDEを使用している人にとっては問題ありませんが、Notepad(またはNotepad ++など)でコードを読んでいる人は、少し研究をしなくても型を調べるのに時間がかかります。

+0

それも私のポイントです。実際、私の例では、これがインターフェイスにプログラミングする唯一の方法です。 – Mank

+0

ええ、私が言ったように、私はそのような状況では使用しません。私は主にLINQクエリのためだけに使用します。 – mkchandler

6

コンパイラが行うことができる唯一の合理的なものは、それが何であるあなたが製品を持っていた場合のような...

class Product : IFirst, ISecond, IThrid 

。私はvarの使用を制限しない、私はどこでもそれを使用します。コードをはるかに読みやすくすると思います。この場合、私はReSharperに全面的に同意します。

7

具体的なProductクラスへの依存が依然として残っているので、メソッド内で具体的なクラスをインスタンス化しているのであれば、実際には "プログラミングする"というわけではありません。インターフェイスを適切にプログラムするには、の新しいインスタンシエーションを、たとえばファクトリまたはIoCを使用して削除する必要があります。あなたはProductタイプIEntityのようにしたい場合は

4

、これを試してみてくださいと述べ

var product = new Product() as IEntity; 

は、はいあなたは、インターフェイスにプログラムする必要がありますが、あなたのケースでは、あなたが直接具体的なタイプをインスタンス化しています。コンクリート型への依存関係を既に作成している場合は、コンクリート型を使用してください。そうでない場合は、ファクトリまたはインジェクションを使用してインタフェースのインスタンスを取得します。 varは、それらをうまく使用できます。たとえば:

public class MyExtremelySimpleFactoryExampleClass 
{ 
    public IEntity Instantiate() 
    { 
    return new Product(); 
    } 
} 

// elsewhere in your code... 
var item = myFactory.Instantiate(); // item is of type IEntity 

は最後に、いや、私はvarが唯一の「特別の事情」で使用されなければならないとは思いません。私はそれが非常に有用であり、ほとんど常にそれを使用することがわかります。

+0

は例外なく鋳造に使用されます。それはvar product =(IEntity)new Product()でなければなりません。 – cbuteau

1

推定される型は実際の型であり、実装または継承する可能性のあるインターフェイスまたは基本クラスはありません。それはインタフェースではなく、型を推論たい場合は、変数の型がIComparable代わりのstringようなものになるだろう

var answer = "42"; 

が、この考えてみましょう。

varキーワードの使用法は、実際の型を推論することに依存している、またはそれは匿名型以外の何のためにそれを使用する意味がありません。タイプが明白である限り、コードをより読みやすくするために使用できますが、タイプが完全にはっきりしていない場合は、使用しないでください。 (上記の私の例は、実際にはstringタイプ名を含んでいないので、灰色の領域です)