Метод ограничения потенциальных значений Enum - PullRequest
6 голосов
/ 14 октября 2011

Можно ли ограничить допустимые значения перечисления, которые может принимать метод.

Скажем, например, у меня есть перечисление, подобное этому:

public enum WEEKDAY {
    SUNDAY,
    MONDAY,
    TUESDAY,
    WEDNESDAY,
    THURSDAY,
    FRIDAY,
    SATURDAY;
}

И скажите, что у меня естьметод, который должен принимать только внутренний набор этих значений:

//Here dayOfWeek should only be Monday - Friday.
public void setWorkDayAlarm(WEEKDAY dayOfWeek) {
}

Я знаю, что вы, очевидно, можете включить действительные значения и в случае по умолчанию ничего не делать.Но есть ли способ (или шаблон) определить в интерфейсе метода, что он принимает только определенное подмножество допустимых перечислений в Java (5+)?

Ответы [ 4 ]

7 голосов
/ 14 октября 2011

Я не знаю, что система типов может помочь вам здесь.Как насчет этого?

public enum DayOfWeek {
    SUNDAY(false), MONDAY(true), TUESDAY(true), WEDNESDAY(true),
    THURSDAY(true), FRIDAY(true), SATURDAY(false);

    private final boolean isWeekday;

    private DayOfWeek(boolean isWeekday) {
        this.isWeekday = isWeekday;
    }

    public boolean isWeekday() {
        return isWeekday;
    }
}

Затем проверьте аргумент:

public void setWorkDayAlarm(DayOfWeek dayOfWeek) {
    if (!dayOfWeek.isWeekday())
        throw new IllegalArgumentException("Need weekday, got " + dayOfWeek);

    // ...
}
3 голосов
/ 14 октября 2011

Сам язык не позволяет создавать подмножества перечислений. Это в первую очередь противоречило бы цели перечисления - иметь определенный набор значений для данного домена.

Что вы можете сделать: Определите другое подходящее перечисление для этого домена и предоставьте разумные перекрестные сопоставления. Чтобы получить идею:

public enum WORKDAY {
    MONDAY(WEEKDAY.MONDAY),
    TUESDAY(WEEKDAY.TUESDAY),
    WEDNESDAY(WEEKDAY.WEDNESDAY),
    THURSDAY(WEEKDAY.THURSDAY),
    FRIDAY(WEEKDAY.FRIDAY);

    final public WEEKDAY weekday;

    WORKDAY(WEEKDAY wd){
        this.weekday = wd;
    }
    static WORKDAY convertWeekday(WEEKDAY weekday){
        // in real live use a static EnumMap
        for(WORKDAY workday: values())
            if( workday.weekday == weekday )
                return workday;
        return null; // or an exception
    }
}

public void setWorkDayAlarm(WORKDAY workDay){ ... }

Хорошая вещь: вызывающая сторона метода преобразования должна иметь дело с этими значениями, которые не отображаются. Ваш метод остается чистым.

1 голос
/ 14 октября 2011

Так как метод, который вы предоставили, является public, допустимо генерировать IllegalArgumentException , если вызывающая сторона дает ему недопустимое значение. Для закрытого метода может произойти сбой утверждения отладки.

0 голосов
/ 14 октября 2011

Сделать это через сигнатуру метода (система типов, как сказал @pholser) в Plain Old Java невозможно.Существуют некоторые фреймворки, такие как CDI, или альтернативные стили программирования, такие как Design By Contract , которые могут выполнять то, что вы просите.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...