Если вы новичок, позвольте мне объяснить шаг за шагом, что происходит здесь.
def myflatten(somelist : List[Any]): List[Any] = somelist flatMap {
case ms: List[_] => flatten(ms)
case e => List(e)
}
Написано пространно:
def myflatten(somelist : List[Any]): List[Any] = somelist flatMap { something =>
something match {
case ms: List[_] => flatten(ms)
case e => List(e)
}
}
Что ms
и e
?
Сначала позвольте мне сломать это.
Вы являетесь плоской карточкой над List[Any]
.
val x = List("Str1", "Str2", "Str3")
val y = x flatMap { elementInList => List(elementInList) }
Это означает, что для каждого элемента в списке вы создаете новый список с этим элементом в нем. Потому что его flatMap
вы по существу получаете те же самые (одни и те же элементы) список назад.
Checkout, что произойдет, если вы используете map
вместо flatMap
:
val x = List("Str1", "Str2", "Str3")
val y = x map { elementInList => List(elementInList) }
val
y
будет:
List(List("Str1"), List("Str2"), List("Str3"))
выписка http://www.brunton-spall.co.uk/post/2011/12/02/map-map-and-flatmap-in-scala/
теперь, глядя на подробном примере :
def myflatten(somelist : List[Any]): List[Any] = somelist flatMap { something =>
something match {
case ms: List[_] => flatten(ms)
case e => List(e)
}
}
вы соответствуете по элементу в списке или в этом случае называетесь something
. вы также соответствуете на элементах type
.
, например
def myMatch(e: Any): String = {
e match {
case x: String => "Its a String: " + x
case y: Int => "Its a Int: " + y
//notice how im using x twice.. its because they're in separate scope!
case x: Boolean => "Its a Boolean: " + x
case _ => "Its something else!"
}
}
вызывать myMatch
с парами "hello"
и он вернется "Its a String: hello"
.
invoke myMatch
с параметром 1
и он вернется "Its a Int: 1"
.
выписка http://docs.scala-lang.org/tutorials/tour/pattern-matching.html
Что e
и ms
?
позволяет взглянуть на ваш код:
def myflatten(somelist : List[Any]): List[Any] = somelist flatMap {
case ms: List[_] => flatten(ms)
case e => List(e)
}
Если элемент в списке, который мы сейчас смотрим, типа List[_]
(так же, как List[Any]
), мы затем выполнить этот блок, flatten(ms)
. ms
- это val
, назначенный элементу после согласования.
Если элемент в списке, который мы сейчас смотрим, типа _
или по существу по умолчанию (case _ =>
), а затем возвращает List(e)
, содержащие один элемент, который является элементом, который мы смотрели.
Это всегда будет возвращать List[List[Any]]
. Который затем сплющивается до List[Any]
.
Я надеюсь, что это помогает,
Rhys