C# 7.0 元组推导

C# 7.0 Tuple Deduction

当我写这行时:

Tuple<string,string> key = (controller, action);

我收到这个错误:

Severity Code Description Project File Line Suppression State Error CS0029 Cannot implicitly convert type '(string controller, string action)' to 'System.Tuple' Project.Web PageMetadata.cs 27 Active

这似乎是 C#7 更新核心的新元组增强功能的相当直接、直观的应用,但它不起作用。我做错了什么?

新的元组功能需要 ValueTuple 类型,即

ValueTuple<string, string> key = (controller, action);

var key = (controller, action);

重要的是要注意 Tuple 是 class 而 ValueTuple 是结构。你不应该混淆它们。有关 C# 7 中的新元组功能的更多详细信息,请参阅此处

使用 ValueTuple<string, string> 而不是 Tuple<string, string>Tuple<T1,T2> is a system type from before C# 7.0; ValueTuple<T1,T2> is the one that supports the new language features. For more details, see the C# Tuple type guide.

如果你真的需要从System.Tuple转换成System.ValueTuple(使用元组语法),或者返回,有扩展方法:ToTupleToValueTuple定义对于小问题。

首先,您在尝试将新样式元组 (ValueTuple) 转换为旧样式元组 (Tuple) 时遇到该错误。

这可以使用 ToTuple() 扩展方法来实现:

Tuple<string,string> key = (controller, action).ToTuple();        

但这可能不是您想要做的。如果你想创建一个新元组的实例,你可以这样做:

ValueTuple<string,string> key = (controller, action);

但是,如果您这样做,您最终仍然会得到名为 Item1Item2 的两个元素,这违背了新元组语法的关键特性之一:命名元素。将其更改为使用 var,然后您将获得命名元素:

var key = (controller, action);
Console.WriteLine(key.controller); // key.controller is now valid

如果您真的不喜欢使用 var(有些人不喜欢),那么您可以直接表达它以仍然获得那些命名元素:

(string controller, string action) key = (controller, action); 
Console.WriteLine(key.controller);