使用带有枚举C#的Switch语句

本文关键字:Switch 语句 枚举 | 更新日期: 2023-09-27 18:24:05

嗨,我正在创建一个控制台应用程序,用户在其中输入一个月的数字,应用程序计算出它是哪个月,并显示答案和一个月中的天数。当switch语句在Main方法中时,我就让它工作了,但现在它显示错误的月份。我有以下代码:

namespace ConsoleCA2{
public enum Months
{
    January = 31,
    February = 28,
    March = 31,
    April = 30,
    May = 31,
    June = 30,
    July = 31,
    August = 31,
    September = 30,
    October = 31,
    November = 30,
    December = 31
};
public class Program
{
    public const string NEWLINE = "'n";     //constant for new line

    static void Main(string[] args)
    {
        try
        {
            //prompt user for month number.
            Console.Write("Enter a Number to find out what Month it is: ");
            //convert users answer to integer
            int userInput = Convert.ToInt16(Console.ReadLine());
            //declare and initalise
            int daysInMonth = 0;
            string answer = String.Empty;
            //call relevent calculation methods
            answer = DetermineMonth(userInput);
            daysInMonth = DetermineDaysInMonth(userInput);
            //Write users answer to screen
            Console.WriteLine(answer);
            //Prompt user, whether they want to know number of days in the
            //month
            Console.Write("Would you like to know the number of days in" +
                " {0}: ", answer);
            //assign users answer to variable
            string userAnswer = Console.ReadLine();
                //Output answer if needed.
                if (userAnswer == "yes".Trim().ToLower())
                {
                    Console.WriteLine("The number of days in {0} is: {1}", 
                        answer, daysInMonth.ToString());
                }
                else if (userAnswer == "no".Trim().ToLower())
                {
                    Console.WriteLine(NEWLINE);
                    Console.WriteLine("You answered No, Have a good day!");
                }
                else
                {
                    Console.WriteLine("Please answer yes or no.");
                }
            Console.Read(); //Pauses screen for user
        }
            //catch any errors.
        catch (Exception err)
        {
            Console.WriteLine("Error" + err.Message);
        }
    }

    /// <summary>
    /// Determines What month the use enters and returns string value
    /// </summary>
    /// <param name="userInput"></param>
    /// <returns>returns the month as string</returns>
    public static String DetermineMonth(int userInput)
    {
        switch (userInput)
        {
            case 1:
                return Months.January.ToString();
            case 2:
                return Months.February.ToString();
            case 3:
                return Months.March.ToString();
            case 4:
                return Months.April.ToString();
            case 5:
                return Months.May.ToString();
            case 6:
                return Months.June.ToString();
            case 7:
                return Months.July.ToString();
            case 8:
                return Months.August.ToString();
            case 9:
                return Months.September.ToString();
            case 10:
                return Months.October.ToString();
            case 11:
                return Months.November.ToString();
            case 12:
                return Months.December.ToString();
            default:
                return "Error";
        }

    }
    /// <summary>
    /// Determines how many days is in selected month as integer
    /// </summary>
    /// <param name="userInput"></param>
    /// <returns>returns how many days in month</returns>
    public static int DetermineDaysInMonth(int userInput)
    {
        switch (userInput)
        {
            case 1:
                return Convert.ToInt16(Months.January);
            case 2:
                return Convert.ToInt16(Months.February);
            case 3:
                return Convert.ToInt16(Months.March);
            case 4:
                return Convert.ToInt16(Months.April);
            case 5:
                return Convert.ToInt16(Months.May);
            case 6:
                return Convert.ToInt16(Months.June);
            case 7:
                return Convert.ToInt16(Months.July);
            case 8:
                return Convert.ToInt16(Months.August);
            case 9:
                return Convert.ToInt16(Months.September);
            case 10:
                return Convert.ToInt16(Months.October);
            case 11:
                return Convert.ToInt16(Months.November);
            case 12:
                return Convert.ToInt16(Months.December);
            default:
                return 0;
        }
    }

旧的switch语句是这样的:

        switch (userInput)
        {
        case 1:
            answer = Months.January.ToString();
            daysInMonth = Convert.ToInt16(Months.January);
            break;
        case 2:
            answer = Months.February.ToString();
            daysInMonth = Convert.ToInt16(Months.February);
            break;
        case 3:
            answer = Months.March.ToString();
            daysInMonth = Convert.ToInt16(Months.March);
            break;
        case 4:
            answer = Months.April.ToString();
            daysInMonth = Convert.ToInt16(Months.April);
            break;
        case 5:
            answer = Months.May.ToString();
            daysInMonth = Convert.ToInt16(Months.May);
            break;
        case 6:
            answer = Months.June.ToString();
            daysInMonth = Convert.ToInt16(Months.June);
            break;
        case 7:
            answer = Months.July.ToString();
            daysInMonth = Convert.ToInt16(Months.July);
            break;
        case 8:
            answer = Months.August.ToString();
            daysInMonth = Convert.ToInt16(Months.August);
            break;
        case 9:
            answer = Months.September.ToString();
            daysInMonth = Convert.ToInt16(Months.September);
            break;
        case 10:
            answer = Months.October.ToString();
            daysInMonth = Convert.ToInt16(Months.October);
            break;
        case 11:
            answer = Months.November.ToString();
            daysInMonth = Convert.ToInt16(Months.November);
            break;
        case 12:
            answer = Months.December.ToString();
            daysInMonth = Convert.ToInt16(Months.December);
            break;
        default:
            answer = "Error";
            break;
    }

这一直有效,直到我改为单独的方法,然后它就走下坡路了。现在,即使我把它放回去,它仍然会把几个月搞混?

如此困惑:S

提前感谢您的帮助。。。如果你能理解混乱的代码:p

使用带有枚举C#的Switch语句

NET框架包含大量的代码。有时很难找到所需的,但已经有东西的可能性很高。而且,虽然搜索需要时间,但这是一段很好的时间,因为你为自己未来的工作提供了有用的知识

CultureInfo.CurrentCulture.DayFormatInfo.MonthNames
日期时间日期当月

using System.Globalization;
static void Main(string[] args)
{
    Console.Write("Enter a Number to find out what Month it is: ");
    int userInput = Convert.ToInt16(Console.ReadLine());
    if(userInput > 0 && userInput < 13)
    {            
         string monthName = CultureInfo.CurrentCulture.DayTimeFormat.MonthNames[userInput-1];
         int daysInMonth = DateTime.DaysInMonth(2013, userInput);
         ......
    }
}

如果你还需要计算闰年,你应该得到年份的输入,但非常简单

使用enum为常量创建符号名称。在这种情况下,这不是你想要的。

我认为你想要的是一个查找表,给定值a,返回值B。在你的情况下,你可以使用几个数组:

string[] monthNames = new string[]
{
    "January", "February", "March", "April", "May", "June",
    "July", "August", "September", "November", "December"
};
int[] monthDays = new int[] {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 };

然后,您可以通过查找获得月份名称和天数:

int userInput = Convert.ToInt16(Console.ReadLine());
if (userInput < 1 || userInput > 12)
    Console.WriteLine("Error: invalid month.");
else
{
    answer = monthNames[userInput-1];
    daysInMonth = monthDays[userInput-1];
}

还有其他方法可以做到这一点,包括在几个月或几天内使用structs或类,但这些都是稍微高级一些的主题。

此外,.NET有一个DateTime结构,它具有所有这些功能以及更多用于处理日期和时间的功能。在生产程序中,你应该使用它,而不是自己滚动。

这是因为您的枚举将所有内容混合在一起。

31和30存在重复值。

下面是一个工作示例(不过还有更多的优化方法。比如使用DateTime类)

public enum Months : int
{
    None = 0,
    January = 1,
    February = 2,
    March = 3,
    April = 4,
    May = 5,
    June = 6,
    July = 7,
    August = 8,
    September = 9,
    October = 10,
    November = 11,
    December = 12
};
public class Program
{
    public const string NEWLINE = "'n";     //constant for new line
    static void Main(string[] args)
    {
        try
        {
            //prompt user for month number.
            Console.Write("Enter a Number to find out what Month it is: ");
            //convert users answer to integer
            int userInput = Convert.ToInt16(Console.ReadLine());
            //declare and initalise
            int daysInMonth = 0;
            Months answer;
            //call relevent calculation methods
            answer = DetermineMonth(userInput);
            if (answer == Months.None) 
            {
                Console.WriteLine("Please enter a value between 1 and 12");
                return;
            }
            daysInMonth = DetermineDaysInMonth(answer);
            //Write users answer to screen
            Console.WriteLine(answer);
            //Prompt user, whether they want to know number of days in the
            //month
            Console.Write("Would you like to know the number of days in {0}: ", answer);
            //assign users answer to variable
            string userAnswer = Console.ReadLine();
            //Output answer if needed.
            if (userAnswer == "yes".Trim().ToLower())
            {
                Console.WriteLine("The number of days in {0} is: {1}", answer, daysInMonth.ToString());
            }
            else if (userAnswer == "no".Trim().ToLower())
            {
                Console.WriteLine(NEWLINE);
                Console.WriteLine("You answered No, Have a good day!");
            }
            else
                Console.WriteLine("Please answer yes or no.");
            Console.ReadLine(); //Pauses screen for user
        }
        //catch any errors.
        catch (Exception err)
        {
            Console.WriteLine("Error" + err.Message);
        }
    }
    /// <summary>
    /// Determines What month the use enters and returns string value
    /// </summary>
    /// <param name="userInput"></param>
    /// <returns>returns the month as string</returns>
    public static Months DetermineMonth(int userInput)
    {
        switch (userInput)
        {
            case 1:
                return Months.January;
            case 2:
                return Months.February;
            case 3:
                return Months.March;
            case 4:
                return Months.April;
            case 5:
                return Months.May;
            case 6:
                return Months.June;
            case 7:
                return Months.July;
            case 8:
                return Months.August;
            case 9:
                return Months.September;
            case 10:
                return Months.October;
            case 11:
                return Months.November;
            case 12:
                return Months.December;
        }
        return Months.None;
    }
    /// <summary>
    /// Determines how many days is in selected month as integer
    /// </summary>
    /// <param name="userInput"></param>
    /// <returns>returns how many days in month</returns>
    public static int DetermineDaysInMonth(Months userInput)
    {
        switch (Convert.ToInt32(userInput))
        {
            case 1:
            case 3:
            case 5:
            case 7:
            case 8:
            case 10:
            case 12:
                return 31;
            case 2:
                return 28;
            case 4:
            case 6:
            case 9:
            case 11:
                return 30;
        }
        return 0;
    }
}

您可能需要考虑将其简化一点,并使您的枚举数与月份数相匹配。然后将当月的天数存储到其他地方。

然后,您可以使用(Months)userInput来获取枚举并消除至少一个switch语句。

您可以使用Dictionary或其他方式存储每个月的天数,只要枚举为每个值存储一个唯一的int即可。

这不是使用枚举的方式。

它们不仅仅是静态键值对:如果是,那么您可以使用的不仅仅是积分类型。不,它们只不过是围绕整型的类型安全包装器。

你的问题是:

public enum Months
{
    January = 31,
    February = 28,
    March = 31,
    April = 30,
    May = 31,
    June = 30,
    July = 31,
    August = 31,
    September = 30,
    October = 31,
    November = 30,
    December = 31
};

这意味着,据CLR所知,1月、3月、5月、7月、8月、10月和12月是完全相同的。四月、六月、九月和十一月也是如此。

正确的方法是这样的:

public enum Months
{
    None = -1,
    January = 1,
    February = 2,
    March = 3,
    April = 4,
    May = 5,
    June = 6,
    July = 7,
    August = 8,
    September = 9,
    October = 10,
    November = 11,
    December = 12
};

然后你的DetermineMonth方法就是这样:

public static Months DetermineMonth(int userInput)
{
    Months temp = (Months)userInput;
    return Enum.IsDefined(typeof(Months), temp) ? temp : Months.None; 
}

然后DetermineDaysInMonth将是这样的:

public static int DetermineDaysInMonth(int userInput)
{
    if (!((Months[])Enum.GetValues(typeof(Months))).Contains((Months)userInput)
        return 0;
    else return DateTime.DaysInMonth(DateTime.Today.Year, userInput);
}

您可以在enum上使用Extension方法来返回天数-

public enum Months
{
    January,
    February,
    March,
    April,
    May,
    June,
    July,
    August,
    September,
    October,
    November,
    December
}
public static class MonthsExtensions
{
    public static int DaysInMonths(this Months month)
    {
        switch (month)
        {
            case Months.January:
            case Months.March:
            case Months.May:
            case Months.July:
            case Months.August:
            case Months.October:
            case Months.December:
                return 31;
            case Months.April:
            case Months.June:
            case Months.September:
            case Months.November:
                return 30;
            case Months.February:
                return 28;
        }
        return 0;
    }

然后你可以得到这样的天数-

int daysInMonths = Months.January.DaysInMonths();