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

如何在Type字典中匹配可空枚举的typeof类型?

反射格式化对象属性时的可空枚举匹配问题

我正在使用反射来确定如何格式化对象的属性。以下是一个formatters字典:

var formatters = new Dictionary<Type, Func<object, object>>()
{
    { typeof(Enum), x => ((Enum)x)?.FormatEnum() },
    { typeof(DateTime?), x => ((DateTime?)x)?.ToShortDateString() },
    { typeof(string), x => x.ToString().ToLower() }
};

大多数类型都能正常工作,但当获取可空枚举TaskStatus的类型时,它的类型不是Enum,而是该枚举自身的名称。我注意到它的基类型是Enum,但不想通过检查基类型来匹配,因为其他大多数类型直接用类型就能匹配成功。

例如,string类型的检查正常:

typeof(string).FullName = "System.String"

但对于TaskStatus枚举:

typeof(Enums.TaskStatus).FullName = "Enums.TaskStatus"

因此typeof(Enum) != typeof(Enums.TaskStatus),导致字典无法找到匹配项。

有没有办法不用添加所有使用的可空枚举类型名称,就能在formatters字典中找到匹配项?

补充完整代码

public class NoteHistory
{
    [JsonProperty("Status")]
    public TaskStatus? TaskStatus { get; set; }
    [JsonProperty("CreatedDate")]
    public DateTime? CreatedDate { get; set; }
    [JsonProperty("Description")]
    public string Description { get; set; }
    public bool IsDeleted { get; set; } // not interested in comparing this
}

public enum TaskStatus
{
    ToDo,
    Done
}

public static void DisplayValues()
{
    var noteHistory1 = new NoteHistory
    {
        TaskStatus = TaskStatus.ToDo
    };

    var noteHistory2 = new NoteHistory
    {
        TaskStatus = TaskStatus.Done
    };

    // Get all properties with JsonProperty attr.
    var propertiesToCompare = typeof(NoteHistory)
        .GetProperties()
        .Where(x => x.CustomAttributes
            .Any(y => y.AttributeType.Name == nameof(JsonPropertyAttribute)));

    var comparers = new Dictionary<Type, Func<object, object, bool>>
    {
        { typeof(string), (x, y) => !string.Equals(x?.ToString(), y?.ToString(), StringComparison.InvariantCultureIgnoreCase) }
    };

    var formatters = new Dictionary<Type, Func<object, object>>()
    {
        { typeof(Enum), x => ((Enum)x)?.FormatEnum() }, // doesn't work
        { typeof(DateTime?), x => ((DateTime?)x)?.ToShortDateString() },
        { typeof(string), x => x.ToString().ToLower() },
    };

    foreach (var propertyToCompare in propertiesToCompare)
    {
        var prop1Value = propertyToCompare.GetValue(noteHistory1);
        var prop2Value = propertyToCompare.GetValue(noteHistory2);

        Func<object, object, bool> comparer;
        comparers.TryGetValue(propertyToCompare.PropertyType, out comparer);

        var hasChanged = comparer?.Invoke(prop1Value, prop2Value) ?? prop1Value != prop2Value;

        if (hasChanged)
        {
            Func<object, object> formatter;
            formatters.TryGetValue(propertyToCompare.PropertyType, out formatter);

            var formattedValue = formatter?.Invoke(noteHistory2);
            // TODO: display the value
        }
    }
}

内容的提问来源于stack exchange,提问作者David Klempfner

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.03 23:19:57