У меня есть тип enum, ReportTypeEnum
который передается между методами во всех моих классах, но затем мне нужно передать это по URL-адресу, чтобы я использовал порядковый метод для получения значения int. После того, как я получу его на другой моей странице JSP, мне нужно преобразовать его обратно в формат, ReportTypeEnum
чтобы я мог продолжить его передачу.
Как я могу преобразовать порядковый номер в ReportTypeEnum
?
Использование Java 6 SE.
Ответы:
Чтобы преобразовать порядковый номер в его представление enum, вы можете сделать это:
Пожалуйста, обратите внимание на границы массива.
Обратите внимание, что каждый вызов
values()
возвращает новый клонированный массив, который может отрицательно повлиять на производительность. Вы можете кэшировать массив, если он будет часто вызываться.Пример кода о том, как кешировать
values()
.Этот ответ был отредактирован, чтобы включить обратную связь, данную внутри комментариев
источник
Это почти наверняка плохая идея . Конечно, если порядковый номер де-факто сохраняется (например, потому что кто-то добавил закладку в URL) - это означает, что вы всегда должны сохранять
enum
порядок в будущем, что может быть неочевидно для сопровождающих кода в дальнейшем.Почему бы не кодировать
enum
использованиеmyEnumValue.name()
(и декодировать черезReportTypeEnum.valueOf(s)
) вместо этого?источник
value
в начале или в правильной алфавитной / логической позиции. (Под логическим я имею в виду, например,TimeUnit
значения имеют логическую позицию)Если я собираюсь использовать
values()
много:Тем временем где.java:
Следите за границами вашего массива.
источник
Suit.values[0] = Suit.Diamonds;
где-то в вашем коде. В идеале этого никогда не случится, но общий принцип не выставлять изменяемые поля все еще сохраняется. Для этого подхода рассмотрите использованиеCollections.unmodifiableList
или подобное вместо этого.Suit values[]
прямо или косвенно (как было упомянуто черезgetValues()
), я работаю с открытым методом, гдеordinal
значение должно быть отправлено как аргумент и вернутьSuit
представление изSuit values[]
. Суть здесь (фрагмент вопроса с самого начала) заключалась в создании типа enum из порядкового номера enumЯ согласен с большинством людей, что использование порядкового номера, вероятно, плохая идея. Обычно я решаю эту проблему, предоставляя enum приватный конструктор, который может принимать, например, значение DB, а затем создавать статическую
fromDbValue
функцию, аналогичную той, что была в ответе Яна.Теперь вы можете изменить порядок без изменения поиска и наоборот.
источник
Вы можете использовать статическую таблицу поиска:
источник
0...(n-1)
, то массив меньше кода и также более читабелен; повышение производительности - это просто бонус.private static final Suit[] VALUES = values();
иpublic Suit fromOrdinal(int ordinal) { return VALUES[ordinal]; }
. Дополнительное преимущество: сбой сразу при неверных порядковых номерах, вместо того, чтобы молча вернуть ноль (Не всегда преимущество. Но часто.)Это то, что я использую. Я не претендую на то, что он гораздо менее «эффективен», чем простые решения выше. Что он делает, так это предоставляет гораздо более четкое сообщение об исключении, чем «ArrayIndexOutOfBounds», когда в решении выше используется недопустимый порядковый номер.
Он использует тот факт, что EnumSet javadoc указывает, что итератор возвращает элементы в их естественном порядке. Есть утверждение, что это не правильно.
Тест JUnit4 демонстрирует, как он используется.
источник
Вот что я делаю на Android с Proguard:
это коротко, и мне не нужно беспокоиться о наличии исключения в Proguard
источник
Вы можете определить простой метод как:
И используйте это как:
источник
тестовый класс
Я ценю, что вы поделитесь с нами, если у вас есть более эффективный код, Мой список огромен и постоянно вызывается тысячи раз.
источник
Таким образом, один из способов - сделать то,
ExampleEnum valueOfOrdinal = ExampleEnum.values()[ordinal];
что работает, и это легко, однако, как уже упоминалось,ExampleEnum.values()
возвращает новый клонированный массив для каждого вызова. Это может быть излишне дорого. Мы можем решить это, кэшируя массив следующим образомExampleEnum[] values = values()
. Также «опасно» разрешать изменение нашего кэшированного массива. Кто-то может написатьExampleEnum.values[0] = ExampleEnum.type2;
Так что я бы сделал это приватным с помощью метода доступа, который не выполняет дополнительное копирование.Вы бы использовали,
ExampleEnum.value(ordinal)
чтобы получить значение enum, связанное сordinal
источник
Каждое перечисление имеет имя (), которое дает строку с именем члена перечисления.
Учитывая
enum Suit{Heart, Spade, Club, Diamond}
,Suit.Heart.name()
дастHeart
.Каждое перечисление имеет
valueOf()
метод, который принимает тип перечисления и строку для выполнения обратной операции:Enum.valueOf(Suit.class, "Heart")
возвращаетсяSuit.Heart
.Почему кто-то будет использовать ординалы, мне не под силу. Это может быть наносекундами быстрее, но это небезопасно, если члены перечисления меняются, поскольку другой разработчик может не знать, что какой-то код полагается на порядковые значения (особенно на странице JSP, процитированной в вопросе, издержки сети и базы данных полностью доминируют время, не используя целое число над строкой).
источник