What advantages does using var have over the explicit type in C#?
Possible Duplicates:
What’s the point of the var keyword?
Use of var keyword in C#
号
我理解数据类型的IEnumerable<...>如何使代码的可读性变差,或者嵌套的泛型看起来有点令人生畏。但是除了代码可读性之外,使用var而不是显式类型还有什么好处呢?似乎通过使用显式类型,您最好传递变量的功能,因为您知道它是什么。
如果这是一个工作场所编码标准,我使用它是为了团队合作。然而,在我自己的项目中,我更喜欢避免使用var。
- 型stackoverflow.com/search?Q=[C%23]+变量
- 型以东十一〔0〕是万恶的缩影。我怀着对匿名类型和查询结果之外的极度仇恨来看待它。现在问我关于dynamic的事。前进。
- 型@安东尼·佩格拉姆那时不使用它。
- 型当我们转移到Visual Studio 2008时,我与之合作的开发团队的其他成员开始对他们声明的所有内容使用var。我讨厌这个关键字,我讨厌调试他们的代码,最终他们的代码花了我两倍的时间来看看他们到底想实现什么。如果他们不编写长度超过500行的函数和方法,并且到处都是var的var关键字,那么情况就不会那么糟糕了。只有编写清晰的代码的开发人员才应该使用var关键字,并在将其放入源代码控制之前测试其代码!你看!
- 型@彼得,在那儿还好吗?
- 型@安德烈,我没有!
- 型类型推断通常通过删除不增加代码可读性的样板文件来提高清晰度。
- 型还有:stackoverflow.com/questions/41479/use-of-var-keyword-in-c
- 型@彼得:听起来"var"不是代码问题的真正来源。
- 型它让我少打字
- 型完全是一种风格。没有好处,因为编译器的结果都是一样的。
- 型@柯克,是的,我是这里的代码管理员,这个角色很快就让人厌倦了!!(如果我没有按揭付款的话,哈哈)@david,你说得对,var关键字不是根本原因,但它没有帮助。我猜另一个可能不好的方面是,如果它在基于反射的环境中使用,代码重构可能突然意味着行为的改变,当var关键字相应地改变它的类型时,这种改变不会被接受。我在以前的一些地方看到了实现,在这些地方审计是通过反射图遍历执行的,并且是通过审计(对象obj)方法执行的。
- 型@使用var的jimmyhoffa不会改变强类型。编译器仍然知道变量的类型。
- 型@阿加旺哦,天哪,我真不敢相信我4年前说过这句话。删除了该评论。从那以后,我学到了haskell和wish.net可以进一步推断类型(我还知道是静态的)。
var的要点是允许匿名类型,如果没有匿名类型,它们就不可能存在,这就是它存在的原因。我认为所有其他的用途都是懒惰的编码。
- 懒惰?它可以用更少的按键来实现相同的功能。从应用程序的角度来看,这是一种原始效率。
- @可以说,如果类型是隐式定义的,那么看到它就有点困难了。我倾向于遵循这样的模式:如果类型是长的和复杂的,例如某个>,并且更容易从变量名中推断出来,那么使用var。否则我显式地指定类型。
- var的另一个优点是不需要添加using语句。例如var car s=getcars();不需要添加"using namespace.car",如果用car替换var,就必须这样做。
- 懒惰=总的效率"我选择一个懒惰的人去做一件艰苦的工作。因为懒惰的人会找到一个简单的方法去做。
使用var作为foreach块的迭代器变量比显式类型名更安全。例如
1 2 3 4 5 6
| class Item {
public string Name;
}
foreach ( Item x in col ) {
Console.WriteLine(x.Name);
} |
此代码可以编译而不发出警告,但仍会导致运行时强制转换错误。这是因为foreach循环同时与IEnumerable和IEnumerable一起工作。前者返回类型为object的值,C编译器只为您在引擎盖下执行到Item的转换。因此,它是不安全的,并且可能导致运行时错误,因为IEnumerable可以包含任何类型的对象。
另一方面,以下代码将只执行以下操作之一
不编译,因为x是类型化为object或其他没有名称字段/属性的类型
编译并确保在枚举时不会出现运行时强制转换错误。
"x"的类型在IEnumerable的情况下为object,在IEnumerable的情况下为T。编译器不执行强制转换。
1 2 3
| foreach ( var x in col ) {
Console.WriteLine(x.Name);
} |
- object不包含字段Name。当然可以吗?
- 问题1:如果var x解决了object,则无法访问Name属性。你必须继续施法。
- @我也得出了同样的结论,即不是阳性的。
- @xander,@anthony我想说的是,使用EDOCX1(0〕1)compile=no runtime cast issue或2)不编译只有2个结果。
- 明白了,你没有说它不会给出运行时错误,只是在编译时不需要对第一种情况进行强制转换…
- 如果他的同僚(没有显示)是IEnumerable
型的话。
- @Xander正确。
- @马修重读了答案…
- @xander,如果您查看代码块,那么没有为col变量赋值。所以你不知道它是什么类型的变量。很可能是List
- : IEnumerable
或ItemCollection : IEnumerable。
- @马修,你还没看见吗?"瓦雅·康迪奥斯…"
我喜欢它,特别是在单元测试中,因为随着代码的发展,我只需要修复声明/分配的右侧。显然,我还必须更新以反映用法的更改,但在声明时,我只需要做一个更改。
它不会对发出的IL产生有意义的变化。这只是一个代码样式的首选项。
首先,我喜欢它,尤其是在处理具有长的、通用的、几乎不可读的名称的类型时,如Dictionary>[]。
没有什么真正的区别。有些人建议使用显式类型,因为它可以使代码维护更容易。然而,推动var的人有这样的立场:"如果我们使用var,就必须使用好的命名约定"。
当然,如果您使用vars的目的是要有良好的命名约定,而这样做失败了,那么在这条路上会更加痛苦。(国际海事组织)
- 在我看来,使用"var"时,好的编码约定比好的命名约定更重要。任何声明的"var"都在当前方法范围内。只要方法相当简洁(应该如此),就不应该很难弄清楚变量引用的是什么。
var只是一种句法上的糖分。在编译时总是知道变量是什么类型。使用var关键字没有其他优势。
- 嗯,还有其他一些优势。例如,能够存储对匿名类型实例的引用,并且仍然能够引用属性。(即使用select子句创建特殊对象的LINQ查询结果)
1 2 3 4 5 6 7 8 9 10 11 12 13 14
| public IAwesome { string Whatever { get; } }
public SoCool : IAwesome { public string Whatever { get; } }
public HeyHey
{
public SoCool GetSoCool () { return new SoCool (); }
public void Processy ()
{
var blech = GetSoCool ();
IAwesome ohYeah = GetSoCool ();
// Now blech != ohYeah, so var is blech and ohYeah is IAwesome.
}
} |
- +因为"哎呀!哦,是的,所以var是blech,而ohyah是iawesome"让我笑了
您可以从模型中抽象出技术性的心理复杂性,以纯粹地关注问题领域。必须确保变量的命名有意义。
除了您提到的可读性方面,"var"还有一个好处,那就是减少了一个微小的代码更改将破坏代码其他部分的可能性。例如,如果重命名类型。或者,如果切换到与前一种类型(例如,从foo[]更改为ienumerable)基本兼容的其他类型,则将代码恢复到可编译状态所需的工作就要少得多。