Я должен сказать, что я не понимаю классы перечисления Scala. Я могу скопировать-вставить пример из документации, но я понятия не имею, что происходит.
object WeekDay extends Enumeration {
type WeekDay = Value
val Mon, Tue, Wed, Thu, Fri, Sat, Sun = Value
}
import WeekDay._
type WeekDay = Value
и зачем мне это писать?val Mon = Value
? Что это значит?WeekDay
объект? И,val day = WeekDay.Mon
, почему это тип WeekDay.Value
, а не тип WeekDay
?признак Enumeration
имеет член типа Value
, представляющий отдельные элементы перечисления (это фактически внутренний класс, но разница здесь не имеет значения).
Таким образом, object WeekDay
наследует этот член типа. Строка type WeekDay = Value
- это просто псевдоним типа. Это полезно, потому что после его импорта в другом месте с помощью import WeekDay._
вы можете использовать этот тип, например:
def isWorkingDay(d: WeekDay) = ! (d == Sat || d == Sun)
Вместо этого минимальная версия была бы следующей:
object WeekDay extends Enumeration {
val Mon, Tue, Wed, Thu, Fri, Sat, Sun = Value
}
и вам не нужно импортировать содержимое object WeekDay
, но тогда вам нужно будет использовать тип WeekDay.Value
и квалифицировать отдельные члены. Таким образом, пример станет
def isWorkingDay(d: WeekDay.Value) = ! (d == WeekDay.Sat || d == WeekDay.Sun)
Второй вопрос касается значения val Mon, ... = Value
. Это действительно очень запутанно, если вы не смотрите на реализацию Enumeration
. Это не назначение типа! Вместо этого он вызывает защищенный метод с тем же именем, Value
, который возвращает конкретный экземпляр типа Value
.
Так получилось, что вы можете написать val a, b, c = foo
в Scala, а для каждого значения a
, b
и c
метод foo
будет вызываться снова и снова. Enumeration
использует этот трюк, чтобы увеличить внутренний счетчик, чтобы каждое значение было индивидуальным.
Если вы откроете документы Scala API для Enumeration
и нажмите Visibility: All
, вы увидите, что этот метод появляется.