带功能方法的枚举(组合类/枚举)

本文关键字:枚举 组合 方法 功能 | 更新日期: 2023-09-27 18:08:41

我可能在这里漏掉了一些要点,如果是这样的话——请把这个讨论作为我问题的一部分。

这是一个简化的、重命名的工作代码示例。GetTicks(…)是一个单独的示例,它可以是任何类型的功能(> 0 < 9的值应该返回一个特定的Enum a.so)。

public static class Something
{
    public enum TypeOf : short
    {
        Minute = 2, Hour = 3, Day = 4, …
    }
    public static long GetTicks(Something.TypeOf someEnum)
    {
        long ticks = 0;
        switch (someEnum)
        {
            case Something.TypeOf.Minute:
                ticks = TimeSpan.TicksPerMinute;
                break;
            case Something.TypeOf.Hour:
                ticks = TimeSpan.TicksPerHour;
                break;
         ....
        }
        return ticks;
    }
}
// This class is called from anywhere in the system.
public static void SomeMethod(string dodo, object o, Something.TypeOf period)
{
    // With the design above
    long ticks = Something.GetTicks(period);
    // Traditional, if there was a simple enum
    if (period == Something.Day)
        ticks = TimeSpan.FromDays(1).Ticks;
    else if (period == Something.Hour)
        ticks = TimeSpan.FromHours(1).Ticks;
}

这个想法是收集与enum有关的功能,尽可能接近enum本身。enum是reason函数。此外,我发现在enum附近寻找这样的功能很容易也很自然。而且,它很容易修改或扩展。

我的缺点是我必须更明确地声明enum,就像Something.TypeOf一样。设计可能看起来不标准?如果enum在类中用于内部使用,它会适用吗?

你怎么才能做得更好呢?我尝试了abstract,基础继承,partial

带功能方法的枚举(组合类/枚举)

如果您不介意编写更多内容,您可以编写扩展方法来扩展enum的接口。

public enum TimeUnit
{
   Second,
   Minute,
   Hour,
   Day,
   Year,
   /* etc */
}
public static class TimeUnitExtensions
{
    public static long InTicks(this TimeUnit myUnit)
    {
         switch(myUnit)
         {
           case TimeUnit.Second:
               return TimeSpan.TicksPerSecond;
           case TimeUnit.Minute:
               return TimeSpan.TicksPerMinute;
            /* etc */
         }
    }
}

这可以在枚举中添加"instance"方法。不过,它比大多数人喜欢的要冗长一些。

请记住,enum应该主要被视为一个命名值。

c#枚举不能很好地这样工作。但是,您可以相当容易地实现自己的"固定值集":

public sealed class Foo
{
    public static readonly Foo FirstValue = new Foo(...);
    public static readonly Foo SecondValue = new Foo(...);
    private Foo(...)
    {
    }
    // Add methods here
}

碰巧,我得到的一个例子与你的非常相似-野田时间的DateTimeFieldType。有时,您甚至可能希望使类不密封,但保留私有构造函数—这允许您仅将子类创建为嵌套类。非常方便地限制继承。

缺点是不能使用switch:(

)