模式匹配中的元组解构
Tuple deconstruction in pattern matching
经过长时间的休息后,我正在研究 c# 中的新功能,并试图了解泛型类型匹配的工作原理。同时我想知道是否可以解构模式中的元组,例如:
string SendIt<T>(T p) => p switch
{
ValueTuple<int, int> t => $"int point {t.Item1}, {t.Item2}", // <- this works
(float x, float y) => $"float point {x}, {y}", // <- this doesn't
_ => $"dunno, type={typeof(T)}",
};
在 does not work
的情况下,您试图将完全未知的东西(T
没有任何限制)解构为两个元素。在这种情况下,编译器将尝试搜索 static void Deconstruct<T>(this T val, out float x, out float y)
中的某处,但会失败(无论如何,我无法想象对于完全未指定的 T
,这样的函数看起来如何)。所以,它不会编译。
第一行(编译)使用强制转换,因此它只会在运行时处理所有内容(如果无法强制转换则不会进入分支)
至于元组解构的问题,那就来吧——修复元组的声明,明确的说它是一个元组,里面有两个元素。
string SendIt<T1, T2>(Tuple<T1, T2> p) => p switch
{
(float x, float y) => $"float point {x}, {y}",
_ => $"dunno, type={typeof(T)}",
};
Console.WriteLine(SendIt(Tuple.Create(2f,3f))); //float point 2, 3
Console.WriteLine(SendIt(Tuple.Create(2,"test"))); //dunno, type=System.Int32
我们还可以通过转换方法走得更远,所以
string SendIt<T>(T p) => p switch
{
ValueTuple<int, int> t => $"int point {t.Item1}, {t.Item2}",
Tuple<float, float>(float x, float y) => $"float point {x}, {y}",
_ => $"dunno, type={typeof(T)}",
};
Console.WriteLine(SendIt(ValueTuple.Create(1,2))); // int point 1, 2
Console.WriteLine(SendIt(Tuple.Create(1f,2f))); //float point 1, 2
Console.WriteLine(SendIt(Tuple.Create(1,2))); dunno, type=System.Tuple`2[System.Int32,System.Int32]
经过长时间的休息后,我正在研究 c# 中的新功能,并试图了解泛型类型匹配的工作原理。同时我想知道是否可以解构模式中的元组,例如:
string SendIt<T>(T p) => p switch
{
ValueTuple<int, int> t => $"int point {t.Item1}, {t.Item2}", // <- this works
(float x, float y) => $"float point {x}, {y}", // <- this doesn't
_ => $"dunno, type={typeof(T)}",
};
在 does not work
的情况下,您试图将完全未知的东西(T
没有任何限制)解构为两个元素。在这种情况下,编译器将尝试搜索 static void Deconstruct<T>(this T val, out float x, out float y)
中的某处,但会失败(无论如何,我无法想象对于完全未指定的 T
,这样的函数看起来如何)。所以,它不会编译。
第一行(编译)使用强制转换,因此它只会在运行时处理所有内容(如果无法强制转换则不会进入分支)
至于元组解构的问题,那就来吧——修复元组的声明,明确的说它是一个元组,里面有两个元素。
string SendIt<T1, T2>(Tuple<T1, T2> p) => p switch
{
(float x, float y) => $"float point {x}, {y}",
_ => $"dunno, type={typeof(T)}",
};
Console.WriteLine(SendIt(Tuple.Create(2f,3f))); //float point 2, 3
Console.WriteLine(SendIt(Tuple.Create(2,"test"))); //dunno, type=System.Int32
我们还可以通过转换方法走得更远,所以
string SendIt<T>(T p) => p switch
{
ValueTuple<int, int> t => $"int point {t.Item1}, {t.Item2}",
Tuple<float, float>(float x, float y) => $"float point {x}, {y}",
_ => $"dunno, type={typeof(T)}",
};
Console.WriteLine(SendIt(ValueTuple.Create(1,2))); // int point 1, 2
Console.WriteLine(SendIt(Tuple.Create(1f,2f))); //float point 1, 2
Console.WriteLine(SendIt(Tuple.Create(1,2))); dunno, type=System.Tuple`2[System.Int32,System.Int32]