Scalaz fractionnement d'un calcul en sous-parties
-
26-09-2019 - |
Question
J'ai un très grand List[A]
et une f: List[A] => List[B]
fonction. Je voudrais partagé ma liste originale en sous-listes avec une taille maximale, appliquer la fonction à chaque sous-liste, à son tour, puis unsplit le résultat dans une grande List[B]
. Ce assez facile:
def split[T](l : List[T], max : Int) : List[List[T]] = //TODO
def unsplit[T](l : List[List[T]]) : List[T] = //TODO
def apply[A, B](l : List[A], f : List[A] => List[B], max : Int) : List[B] = {
unsplit(split(l, max).map(f(_)))
}
Je me demandais si scalaz fourni des trucs standard pour faire de la boîte? En particulier, la méthode apply
?
La solution
unsplit
juste MA#join
, pour tout M[M[A]]
où M
est un Monad
.
split
n'existe pas hors de la boîte. Ce qui suit est une manière détournée de le faire, plus de démontrer des concepts Scalaz. Il déclenche en fait un débordement de pile dans le compilateur pour le moment!
val ls = List(1, 2, 3, 4, 5)
val n = 5
def truesAndFalses(n: Int): Stream[Boolean] =
Stream.continually(true.replicate[Stream](n) |+| false.replicate[Stream](n)).join
val grouped: List[List[Int]] = {
var zipped: List[(Int, Boolean)] = ls.zip(truesAndFalses(2))
var groupedWithBools: List[List[(Int, Boolean)]] = zipped splitWith {_._2}
groupedWithBools ∘∘ {pair: (Int, _) => pair._1}
}
val joined: List[Int] = grouped ∘∘ {_ * 2} join
Autres conseils
Que diriez-vous ceci:
def split[T](ls: List[T],max: Int): List[List[T]] = ls.grouped(max).toList
def unsplit[T](ls: List[List[T]]): List[T] = ls.flatMap(identity)
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow