c# 8.0 switch 表达式 return 类型和空值

c# 8.0 switch expression return type and null value

我正在尝试了解 C# 8.0 switch 表达式的工作原理,但遇到了几个问题。

  1. 为什么在默认情况下不能使用 null 值?编译器抛出 Cannot convert null to 'int' because it is a non-nullable value type 错误。
  2. 为什么它试图将空值转换为 int 而函数的 return 类型是 'double?'?

这是我正在使用的函数:

public static double? SwitchFunction(int x) =>
    x switch
    {
        1 => 1,
        _ => null
    };

在 switch 表达式中,所有可能的值都必须(隐式转换为)相同的类型。因为您的第一个案例是 1 => 1, 并且您没有将整数文字转换为 int 以外的类型,所以其余案例也将被假定为 int。您需要将 1 转换为 (double?) 以使编译器将其余情况也解释为 double?,一种可为 null 的类型 - 这将解决您的两个问题。

您遇到了条件表达式中经常遇到的问题。

// Compiler Error CS0173
// Type of conditional expression cannot be determined because 
// there is no implicit conversion between 'int' and '<null>'
//
// var d2 = i == 1 ? 1 : null; 

// This works
var d2 = i == 1 ? 1 : (double?) null;

要解决 switch 表达式中的问题,您可以通过指定 null 的类型来帮助编译器。

int i = 2;
var d = i switch
{
    1 => 1,
    _ => (double?)null
};

我遇到了同样的问题,导致了不同的错误消息:"No best type was found for the switch expression"。

var isRequired = someIntValue switch
    {
      0 => null,
      1 => false,
      2 => true,
      _ => throw new NotSupportedException(),
    };

在阅读此处的答案之前,我无法理解此错误消息。编译器无法确定 isRequired 的类型应该是什么。我的意图是 bool?。将代码更改为此会使错误消息消失:

var isRequired = someIntValue switch
    {
      0 => (bool?)null,
      1 => false,
      2 => true,
      _ => throw new NotSupportedException(),
    };

另一方面,我可以告诉编译器我想要什么:

bool? isRequired = someIntValue switch
    {
      0 => null,
      1 => false,
      2 => true,
      _ => throw new NotSupportedException(),
    };

我在 GitHub 上看到他们打算在未来的版本中解决这个问题。