Java 使用字符串计算枚举?

Java 使用字符串计算枚举?,java,eclipse,enums,constants,Java,Eclipse,Enums,Constants,我试图使用字符串来计算字符串内容是否等于我声明的枚举类型。然而,我在Eclipse中遇到一个错误,它试图强迫我将nameOfMonth创建为枚举常量。对于我来说,使用enum似乎更容易,而不是编写代码专门声明一月为#1,二月为#2等等。是否有一种方法可以使用用户定义的字符串并将其与枚举进行比较?例如,在下面的代码中,如果参数字符串nameOfMonth等于一月,我希望它提取索引位置并添加一个 代码如下: package ProgrammingChallenges; public cla

我试图使用字符串来计算字符串内容是否等于我声明的枚举类型。然而,我在Eclipse中遇到一个错误,它试图强迫我将nameOfMonth创建为枚举常量。对于我来说,使用enum似乎更容易,而不是编写代码专门声明一月为#1,二月为#2等等。是否有一种方法可以使用用户定义的字符串并将其与枚举进行比较?例如,在下面的代码中,如果参数字符串nameOfMonth等于一月,我希望它提取索引位置并添加一个

代码如下:

    package ProgrammingChallenges;

public class Month
{
    enum MONTH
    {
        January, February, March, April, May, June, July, August, September, October, November, December
    }

    private int monthNumber;

    public Month()
    {
        monthNumber = 1;
    }

    public Month(int monthNumber)
    {
        if (monthNumber < 1 || monthNumber > 12)
            this.monthNumber = 1;
        else
            this.monthNumber = monthNumber;

    }

    public Month(String nameOfMonth)
    {
        if(nameOfMonth.equals(MONTH.nameOfMonth))
            this.monthNumber = namOfMonth.ordinal() + 1;
    }

}
包编程挑战;
公课月
{
枚举月
{
一月、二月、三月、四月、五月、六月、七月、八月、九月、十月、十一月、十二月
}
蒙特努姆私人酒店;
公众月
{
月数=1;
}
公众月(国际月数)
{
如果(月数<1 | |月数>12)
此.monthNumber=1;
其他的
this.monthNumber=monthNumber;
}
公共月份(字符串名称OfMonth)
{
如果(月名等于月名)
this.monthNumber=namOfMonth.ordinal()+1;
}
}
Enum.valueOf
您可以使用枚举的方法

public Month(String nameOfMonth)
{
   this.monthNumber = MONTH.valueOf(nameOfMonth).ordinal() + 1;
}
这里不需要if语句,只需直接使用enum的Java内置的
valueOf
static方法来获取对应于字符串的enum。如果
nameOfMonth
与枚举不匹配,它将抛出异常:

java.lang.IllegalArgumentException: No enum constant com.yourclass.yourenum.the_invalid_enum_name
    at java.lang.Enum.valueOf(Unknown Source)
根据,如果用户传递一个无效字符串,这将抛出一个
IllegalArgumentException
,这似乎是一个拟合错误。(注意,
MONTH.valueOf(str)
只调用
Enum.valueOf(MONTH,str)

然而,我不明白你为什么需要一个月的单独课程。你为什么不把
Month
改为
enum
?即使在这个类上有额外的方法,也应该能够像在当前类实现中一样将这些方法添加到枚举中。从技术上讲,Java枚举只是具有私有构造函数和静态定义的实例集的类的特例,因此您应该能够使用枚举完成所有需要的操作

在“默认”情况下,您可以使用
Month.janur
,而不是当前的构造函数,当您希望通过索引获取月份时,您可以使用
Month.values()[i-1]
,当您使用字符串时,您可以使用
Month.valueOf(str)
。您还可以将静态帮助器方法添加到枚举中,以封装每个案例。以下是我所描绘的:

public enum Month {
    January, February, March, April, May, June, July, August, September, October, November, December;

    public static Month getDefault() {
        return January;
    }

    public static Month fromNumber(int monthNumber) {
        try {
            return Month.values()[monthNumber-1];
        } catch (ArrayIndexOutOfBoundsException e) {
            return getDefault();
        }
    }

    public static Month fromString(String nameOfMonth) {
        try {
            return valueOf(nameOfMonth);
        } catch (IllegalArgumentException e) {
            return getDefault();
        }            
    }
}

对于那些感兴趣的人来说,这就是我最终解决问题的方式。没有你所有精彩的回答,我不可能做到

MONTH[] months = MONTH.values();

for (MONTH m : months)
        if (m.toString().equals(nameOfMonth))
            this.monthNumber = MONTH.valueOf(nameOfMonth).ordinal() + 1;

这是对Simon答案的评论吗?当您可以简单地使用'MONTH.valueOf`?时,为什么要使用
Enum.valueOf
?@SimonAndréForsberg-它避免了额外的方法调用。
MONTH.valueOf
只是将其参数传递给
Enum.valueOf
。您可以使用
javap
轻松检查这一点。然而,JIT编译器可能足够聪明,可以内联它,所以现在我考虑一下,它可能不会产生真正的区别。所以我想我应该在传递参数之前进行检查以确保它是有效的枚举?或者这种方法在一般情况下是不好的做法?@SamHenderson-您可以事先进行检查,或者捕获抛出的
InvalidArgumentException
。另外,请检查我的编辑。我认为重构一点并添加静态助手方法在这里会有很多好处。顺便说一句,现在Java 8和更高版本中内置了这样一个枚举:它循环遍历所有枚举值,这是不必要的。
MONTH[] months = MONTH.values();

for (MONTH m : months)
        if (m.toString().equals(nameOfMonth))
            this.monthNumber = MONTH.valueOf(nameOfMonth).ordinal() + 1;