You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何优雅地根据泛型参数类型实现分支判断?

问题描述

我希望根据泛型参数的类型进行分支判断 我找到了一种可行且能通过测试的实现方式(*1)(编辑补充:该方式对string类型不生效,可查看@dbc的评论):

public static string HelpWithThis<T>(this DummyClass<T> _)
    =>
    (T)default! switch // <- 我认为这是代码异味
    {
        DateOnly => "This day",
        TimeOnly => "This hour",
        int or float => "This number",
        _ => "This",
    };    

但我并不喜欢对default!进行类型转换的写法。

能否有人指导我如何用更优雅的语法重写这个函数?

测试

(*1)以下是完整的测试代码及复现步骤:

初始化项目命令

dotnet new xunit -o gentyp
cd gentyp
dotnet add package FluentAssertions

测试代码

// UnitTest1.cs
using FluentAssertions;
namespace gentyp;

public class DummyClass<T>{}
public static class DummyExtensions
{
    public static string HelpWithThis<T>(this DummyClass<T> _)
        =>
        (T)default! switch
        {
            DateOnly => "This day",
            TimeOnly => "This hour",
            int or float => "This number",
            _ => "This",
        };    
}

public class UnitTest1
{
    [Fact]
    public void Test1()
        =>
        new DummyClass<int>()
        .HelpWithThis()
        .Should()
        .Be("This number");
}

解决方案

方案1:直接基于typeof(T)判断

避开默认值转换,直接针对泛型参数的类型做分支,逻辑更清晰:

public static string HelpWithThis<T>(this DummyClass<T> _)
    => typeof(T) switch
    {
        _ when typeof(T) == typeof(DateOnly) => "This day",
        _ when typeof(T) == typeof(TimeOnly) => "This hour",
        _ when typeof(T) == typeof(int) || typeof(T) == typeof(float) => "This number",
        _ => "This",
    };

方案2:使用default(T)做模式匹配

保留模式匹配风格,同时修复string类型不生效的问题:

public static string HelpWithThis<T>(this DummyClass<T> _)
    => default(T) switch
    {
        DateOnly => "This day",
        TimeOnly => "This hour",
        int or float => "This number",
        string => "This text",
        _ => "This",
    };

注:原写法中(T)default!对引用类型(如string)会生成null,而模式匹配中string分支需要匹配非空值,改用default(T)后,default(string)就是null,结合C#的空兼容模式匹配逻辑,能正确命中string分支。

方案3:针对值类型用TypeCode简化(可选)

如果主要处理常见值类型,可借助Type.GetTypeCode减少重复的typeof判断:

public static string HelpWithThis<T>(this DummyClass<T> _)
{
    var typeCode = Type.GetTypeCode(typeof(T));
    return typeCode switch
    {
        TypeCode.Int32 or TypeCode.Single => "This number",
        _ when typeof(T) == typeof(DateOnly) => "This day",
        _ when typeof(T) == typeof(TimeOnly) => "This hour",
        _ => "This",
    };
}

此方案对DateOnly、TimeOnly这类新增值类型需要额外判断,因为它们的TypeCode是Object。

内容的提问来源于stack exchange,提问作者dani herrera

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.18 03:52:36