【问题标题】:C# 8.0 switch expression based on input typeC# 8.0 基于输入类型的 switch 表达式
【发布时间】:2020-10-13 08:04:53
【问题描述】:

是否可以根据输入类型在 C# 8 中创建switch expression

我的输入类如下所示:

public class A1
{
    public string Id1 {get;set}
}

public class A2 : A1
{
    public string Id2 {get;set}
}

public class A3 : A1
{
    public string Id3 {get;set;}
}

我想根据输入类型(A1A2A3)运行不同的方法:

var inputType = input.GetType();
var result = inputType switch
{
       inputType as A1 => RunMethod1(input); // wont compile, 
       inputType as A2 => RunMethod2(input); // just showing idea
       inputType as A3 => RunMethod3(input);

}

但它不会工作。任何想法如何根据输入类型创建开关或开关表达式?C

【问题讨论】:

  • 尝试首先使用最具体的类型 (A3) 启动开关,然后逐步降低到最不具体的 (A1)
  • 但我的代码无法编译,我只是展示了想法
  • 哦,我现在看到了,替换为 is

标签: c# c#-8.0


【解决方案1】:

您可以使用模式匹配,首先检查最具体的类型。

GetType 是不必要的:

var result = input switch
{
    A2 _ => RunMethod1(input),
    A3 _ => RunMethod2(input),
    A1 _ => RunMethod3(input)    
};

然而,一种更面向对象的方法是在类型本身上定义一个方法:

public class A1
{
    public string Id1 { get; set; }
    public virtual void Run() { }
}

public class A2 : A1
{
    public string Id2 { get; set; }
    public override void Run() { }
}

那就简单了:

input.Run();

【讨论】:

  • 好主意,但您的代码无法编译。我收到此错误:The Pattern has already been handled by previous arm of switch expression
  • @michasaucer 它编译得很好:dotnetfiddle.net/1dGHUz
  • 你的答案也为我编译......所以现在我需要弄清楚为什么它不会出现在我的场景中(我只是在 SO 中粘贴了基本示例)。谢谢!
  • @JohnathanBarclay 如果您将实例更改为 A2A3 it wont compile 请参阅我的回答中“注释”的第二点。
  • @Jamiec 是的,我可能应该在我的小提琴中明确键入变量。
【解决方案2】:

你可以,但在这样的继承层次结构中,你需要从最具体的开始,然后向下移动:

A1 inputType = new A2();
var result = inputType switch
{
    A3 a3 => RunMethod(a3),
    A2 a2 => RunMethod(a2),
    A1 a1 => RunMethod(a1)
};

注意

  • inputType 是一个实例,而不是Type 的实例
  • inputType 被键入为基类,但可以是任何 A1-3 的实例。否则你会得到一个编译器错误。

现场示例:https://dotnetfiddle.net/ip2BNZ

【讨论】:

    猜你喜欢
    • 2020-03-14
    • 1970-01-01
    • 2020-07-14
    • 2019-08-25
    • 1970-01-01
    • 1970-01-01
    • 2019-10-29
    • 2021-05-18
    • 1970-01-01
    相关资源
    最近更新 更多