Scalaz предоставляет метод с именем fold
для различных ADT, таких как Boolean
, Вариант [_]
, Проверка [_, _]
, Либо [_, _]
и т. Д. Этот метод в основном принимает функции, соответствующие всем возможным случаям для данного ADT. Другими словами, сопоставление с образцом, показанное ниже:
x match {
case Case1(a, b, c) => f(a, b, c)
case Case2(a, b) => g(a, b)
.
.
case CaseN => z
}
эквивалентно:
x.fold(f, g, ..., z)
Некоторые примеры:
scala> (9 == 8).fold("foo", "bar")
res0: java.lang.String = bar
scala> 5.some.fold(2 *, 2)
res1: Int = 10
scala> 5.left[String].fold(2 +, "[" +)
res2: Any = 7
scala> 5.fail[String].fold(2 +, "[" +)
res6: Any = 7
В то же время существует операция с тем же именем для Traversable [_]
, который проходит по коллекции, выполняя определенную операцию над ее элементами и накапливая значение результата. Например,
scala> List(2, 90, 11).foldLeft("Contents: ")(_ + _.toString + " ")
res9: java.lang.String = "Contents: 2 90 11 "
scala> List(2, 90, 11).fold(0)(_ + _)
res10: Int = 103
scala> List(2, 90, 11).fold(1)(_ * _)
res11: Int = 1980
Почему эти две операции идентифицируются одним и тем же именем - fold
/ катаморфизм? Я не вижу никаких сходств / отношений между ними. Что мне не хватает?