2010-05-14 67 views
2

我有一個非常大的List[A]和函數f: List[A] => List[B]。我想將分割爲將我原來的列表分成最大大小的子列表,依次將這個函數應用到每個子列表中,然後將非分割的結果合併成一個大的List[B]。這很簡單:斯卡拉斯分裂計算分部分

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(_))) 
} 

我想知道scalaz是否提供標準的東西要做到這一點開箱?特別是apply方法?

回答

3

unsplit它只是MA#join,對於任何M[M[A]]其中MMonad

split開箱即用不存在。以下是關於這樣做的一個方面,更多的是展示一些Scalaz概念。它現在實際上觸發了編譯器中的堆棧溢出!

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 
+0

麻煩的是我的'f'是'M [A] => M [B]':我在scalaz中看不到任何東西可以幫助解決這個問題(我只看到像A => M [B] ''''M [A => B]'等) – 2010-05-14 15:17:35

+0

'val f:List [A] => List [B] = ...; (分組映射f join):列出[B]' – retronym 2010-05-14 15:26:10

1

如何:

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) 
+0

恩,恩,是的。我說這很容易 - 我問斯卡拉茨是否有什麼可以實現這個開箱即用(可能推廣到其他單子) – 2010-05-14 11:02:25

+0

我想說ls.grouped(max)就像分裂(ls,max)一樣簡潔 – 2010-05-14 15:28:40