Переключатель Java без выражения

В GoLang у вас может быть переключатель без выражения, где случаи заменяют ряд каскадных операторов if.

      t := time.Now()
switch {
case t.Hour() < 12:
    fmt.Println("It's before noon")
default:
    fmt.Println("It's after noon")
}

В Java 19 я могу смоделировать это с помощью такого хака, используя сопоставление шаблона переключения с «защищенным шаблоном», и когда основное выражение всегда истинно, а защищенный шаблон выполняет реальную работу.(Или в Java 17, но с использованием&&вместоwhen)

      int num=5;
switch (System.out) {
    case Object o when num>100 -> System.out.println("Big");
    case Object o when num>50 -> System.out.println("Med");
    default -> {System.out.println("Small");}
}

Очевидно, что эти простые случаи могут быть записаны без переключателя, но когда у вас есть длинная последовательность if-else-if=else, не обязательно для одной и той же переменной, такая структура может быть более лаконичной.

Кто-нибудь знает более приятный способ сделать это?

1 ответ

Есть несколько принципов, которые я могу придумать, которые могут помочь в принятии решений в подобных ситуациях:

  1. Избегайте чрезмерной инженерии
  2. Принцип наименьшего удивления
  3. Используйте правильный инструмент для работы

Оператор switch используется для выполнения различных путей кода на основе возможных значений конкретной переменной. Расширение было придумано, чтобы добавить гибкости и лаконичности этому механизму, но первоначальная цель механизма осталась прежней: включить возможные значения конкретной переменной.

Само понятие «переключатель» основано на идее более чем одного результата, который чем-то контролируется; в случае оператора это что-то является выражением переключения. Если выражения переключения нет, то это не переключатель, а набор взаимоисключающих правил.

Еще одной идеей изобретения оператора была возможность оптимизации. Первоначальные реализации операторов использовали высокоэффективные таблицы поиска, поэтому они могли работать только с. Современные операторы switch работают с более сложными значениями, но при наличии единственного управляющего выражения switch все еще остается некоторая возможность оптимизации. Ничего подобного не происходит, когда нет выражения switch.

Когда я вижу оператор switch, я ожидаю увидеть различные действия, основанные на разных значениях конкретной переменной; Я не ожидаю, что там что-то делается. Если я изучу код и замечу, что мои ожидания не оправдались, я сильно удивлюсь. Разочарован даже.

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


Тот факт, что golang позволяет создавать бессмысленныезаявления абсолютно ничего не значат для меня. Многие языки делают бесполезный выбор. Многие языки даже не имеют какой-либо конкретной причины существования. Многие люди считают «идиоматический» способ ведения дел на конкретном языке самоцелью, хотя это не так. Если вы испытываете искушение взять идиоматическое свойство вашего любимого языка и применить его к другим языкам, сначала спросите себя, имело ли это свойство какое-либо значение даже в исходном языке. Часто это не так.

Другие вопросы по тегам