out var _和out_有什么区别?

6
在C# 7中,我们可以这样做:
byte.TryParse(p.Value, out _)

or like this

byte.TryParse(p.Value, out var _)

有什么区别吗?


3
有区别。你是否使用这两种方式编写了相同的代码,并成功编译运行了? - Ben Voigt
2
在第一种语法中,您将不得不在调用之前单独声明“_”,而在第二种语法中它也将被声明。 - FaizanHussainRabbani
2
@BenVoigt,我不同意这个是一个重复项(至少不是标记为重复项的那个),_在C# 7中被省略作为“out”参数。 - Paul Kertscher
2
@BenVoigt 我不明白为什么重复回答这个问题。那么,这里有什么区别呢? - Evk
2
我同意Paul的观点。 - Jaliya Udagedara
显示剩余7条评论
2个回答

9

它们的区别在于如何处理一个名为_的现有变量。

string _;

int.TryParse("123", out var _); // legal syntax for discard
int.TryParse("123", out _); // compile error, string _ is incompatible with out int parameter

或者

int _;

int.TryParse("123", out var _); // discard
Console.WriteLine(_); // error: variable is not assigned
int.TryParse("123", out _); // passes existing variable byref
Console.WriteLine(_); // ok: prints "123"

这是因为 out _ 已经有了一定的含义,所以这门语言要保持与旧含义的向后兼容。但是在 C# 7 中,out typename identifier 是新语法,因此没有向后兼容的限制。

感谢您的详细说明,我承认我没有考虑到那种情况。 - Paul Kertscher

5
与其他评论中所说的不同:没有区别。它们都产生完全相同的IL。
两者
byte.TryParse(p.Value, out _);
Console.WriteLine(_);

并且。
byte.TryParse(p.Value, out var _);
Console.WriteLine(_);

在C#7中,使用_将产生编译错误,因为_并不打算被使用。

_的使用不仅限于输出参数,还可以用于返回值(正如Evk指出的那样)。

byte.TryParse(p.Value, out var _); // I don't care about the out variable
_ = SomeMethod(); // I don't care about the return value

这里有一个很好的答案,涵盖了大多数关于省略参数的问题,在这里

备注: 我更喜欢使用out _而不是out var _,因为out _out var 合法变量名之间存在明显的语法区别。

编辑

显然我不是完全正确的。有一些微妙的区别,请参见Ben Voigts的答案


2
_ = SomeMethod() 的作用是明确表达您不关心结果(而不是无意中忘记了它)。 它可以在任何地方使用(我的意思是只要 void Main() { _ = 123;} 编译没有问题,不需要任何 out _ 等等,因此它与 out var _ 块无关)。 - Evk
2
“out var identifier” 在一些预发布版本中是合法的,但在 C# 6 中不再支持。C# 7 是第一个允许使用 out 变量(也称为内联声明)的正式版本。半官方参考资料 - Ben Voigt
3
这个答案在多个方面都是错误的。这些代码行不相等,而关于C# 6的说法也是有问题的。 - Ben Voigt
3
在C# 6中,它们都是无效的。第一个无效是因为“_”是未声明的标识符,第二个无效是因为“out typename identifier”语法非法。 - Ben Voigt
@BenVoigt 嗯,是的,变量必须在某个地方声明为 byte _;。就像无论 p 是什么都必须声明一样。我以为这是默认的,但你说得对。 - Rufus L
显示剩余2条评论

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接