2016-10-13 5 views
1

型崩れ機能の概要は、recursively transform a tree, by applying a given functioneverywhere機能の使用例が含まれています型崩れどこでも非同期計算

object inc extends ->((i: Int) => i + 1) 

everywhere(inc)(tree) 

私の質問:私たちはscala.concurrent.Future[Int]を返すasyncInc機能を持っていた場合、どのように1はasyncEverywhere機能を実装することができ変更されたTreeFutureが返されますか?以下のようになります

使用方法は次のとおりです。

object asyncInc extends ->((i: Int) => Future { i + 1 }) 

val treeFuture: Future[Tree[Int]] = asyncEverywhere(asyncInc)(tree) 

答えて

1

私はasyncEverywhereメソッドを記述した場合、私はそれに渡された異なる機能で、二回everywhereを呼び出します。

最初のものは、副作用の同一性関数です。 副作用として適切なFutureを開始し、それを変更可能なリストに追加します。 トラバーサルの最初のパスが完了すると、私はFutureのリストを取得します。

Future.sequenceと呼ぶと、Futureのリストに変換できます。このFuturemapを呼び出して、 の方法でリストを変換します。 - 私はTreeeverywhereを別の機能で呼び出します。その2番目の関数は、左から順に、その結​​果をリストから抜き出します(これは変更可能なリストです)。リストのサイズは処理される要素の数と一致するためです。

import scala.concurrent._ 
import scala.concurrent.ExecutionContext.Implicits.global 
import scala.concurrent.duration._ 
import scala.language.postfixOps 

def asyncEverywhere[T](asyncF: T => Future[T], tree: Tree[T]) 
    (implicit ec: ExecutionContext) = { 

    val queue = scala.collection.mutable.Queue[Future[T]]() 

    object enqueueFutures extends ->({ (i: T) => 
    queue.enqueue(asyncF(i)) 
    i 
    }) 

    everywhere(enqueueFutures)(tree) 

    Future.sequence(queue) map { q => 
    object dispenseResults extends (T -> T)(_ => q.dequeue()) 
    everywhere(dispenseResults)(tree) 
    } 
} 

println(Await.result(
    asyncEverywhere(
    (i: Int) => Future { i + 1 }, 
    tree), 
    1 minute)) 
:ここ

はそのように見えることができる方法です

関連する問題