在与同事讨论了c# 3中var关键字的使用后,我想知道人们对通过var适当使用类型推断的看法是什么?

例如,我很懒地在有问题的情况下使用var,例如:-

foreach(var item in someList) { // ... } // Type of 'item' not clear.
var something = someObject.SomeProperty; // Type of 'something' not clear.
var something = someMethod(); // Type of 'something' not clear.

var更合法的用法如下:-

var l = new List<string>(); // Obvious what l will be.
var s = new SomeClass(); // Obvious what s will be.

有趣的是,LINQ似乎是一个灰色区域,例如:-

var results = from r in dataContext.SomeTable
              select r; // Not *entirely clear* what results will be here.

结果很明显,因为它将是一个实现IEnumerable的类型,但它并不完全明显,与var声明一个新对象的方式相同。

当涉及到对象的LINQ时,情况就更糟了,例如:-

var results = from item in someList
              where item != 3
              select item;

这并不比等价的foreach(var item in someList){//…}相当于。

这里有一个关于类型安全的真正问题——例如,如果我们将该查询的结果放在一个接受IEnumerable<int>和IEnumerable<double>的重载方法中,调用者可能会无意中传入错误的类型。

Var确实保持强类型,但问题是,在定义中不立即显示类型是否危险,当重载意味着当你无意中将错误的类型传递给方法时,编译器可能不会发出错误,这种情况会被放大。


当前回答

为什么var不应该仅仅被用作“输入快捷方式”,而应该被用于它们主要设计的场景:Resharper(至少v4.5)如果一个类型被表示为var,就无法找到它的用法。这在重构或分析源代码时可能是一个真正的问题。

其他回答

这并不坏,这更多的是一种风格上的东西,往往是主观的。当你使用var或不使用var时,它会增加不一致性。

另一个值得关注的情况是,在下面的调用中,你不能仅通过查看CallMe返回的代码来判断类型:

var variable = CallMe();

这是我对var的主要抱怨。

当我在方法中声明匿名委托时,我使用var,在某种程度上var看起来比我使用Func更干净。考虑下面的代码:

var callback = new Func<IntPtr, bool>(delegate(IntPtr hWnd) {
   ...
});

编辑:根据Julian的输入更新最后一个代码样例

当你将鼠标悬停在“var”上时,VS2008 w/resharper 4.1在工具提示中有正确的输入,所以我认为当你寻找一个类的所有用法时,它应该能够找到这个。

虽然还没有测试它是否这样做。

var很困难的一个具体情况是:离线代码审查,特别是在纸上完成的代码审查。

你不能依赖鼠标的移动。

这纯粹是为了方便。编译器将推断类型(基于右边表达式的类型)。

var是处理匿名类型的方法,无论是否来自LINQ语句。任何其他用途在很大程度上取决于谁将阅读您的代码以及有哪些指导方针。

如果你是唯一的观众,或者你的观众对使用var很熟悉,或者非常熟悉你的代码,那么我想这没有关系。如果你像这样使用:var s = new SqlConnection(),那么这在很大程度上无关紧要,可能会提高代码的可读性。如果人们不太挑剔,他们可以做一些工作来了解不明显的类型(这在大多数情况下是不需要的,你在下面的语句中如何使用它通常会解释一切),那么它是好的。

但是如果你有挑剔的,思想封闭的队友,他们喜欢抱怨,或者如果你公司的设计准则特别禁止在类型不明显时使用var,那么你很可能会遇到强烈的反对。

如果使用var会让你的代码难以阅读,你可能会因为使用var而受到伤害,即使这可能是你的应用程序设计的问题。

如果var引入了歧义(有点像你的IEnumerable/IEnumerable例子),不要使用它,而是显式地使用它。但var确实有它的便利,在某些情况下,恕我直言,它甚至可以通过减少混乱来提高可读性。