Create the future without launching it

This is a continuation of my previous question.

Suppose I want to create a future using my function, but I do not want to start it immediately (that is, I do not want to call val f = Future { ... // my function} .

Now I see that this can be done as follows:

  val p = promise [Unit]
 val f = p.future map {_ => // my function here}

Is this the only way to create the future with my function without fulfilling it?

+6
source share
6 answers

You can do something like this

 val p = Promise[Unit]() val f = p.future //... some code run at a later time p.success { // your function } 

LATER EDIT:

I think the template you are looking for can be encapsulated as follows:

 class LatentComputation[T](f: => T) { private val p = Promise[T]() def trigger() { p.success(f) } def future: Future[T] = p.future } object LatentComputation { def apply[T](f: => T) = new LatentComputation(f) } 

You would use it as follows:

 val comp = LatentComputation { // your code to be executed later } val f = comp.future // somewhere else in the code comp.trigger() 
+5
source

You can always delay creation with closure, you cannot get the future object straight ahead, but you will get a handle to call later.

 type DeferredComputation[T,R] = T => Future[R] def deferredCall[T,R](futureBody: T => R): DeferredComputation[T,R] = t => future {futureBody(t)} def deferredResult[R](futureBody: => R): DeferredComputation[Unit,R] = _ => future {futureBody} 
+3
source

If you think too much about performance control, maybe you should use actors instead?

Or perhaps you should use Promise instead of Future : a Promise can be passed on to others while you continue to β€œexecute” it later.

+2
source

You should also give the Promise.completeWith .

You already know how to use p.future onComplete mystuff .

You can call this from another future using p completeWith f .

+2
source

Or just use the usual methods that return futures, and run them sequentially, using something like understanding (consistent evaluation of the site)

+1
source

This is a well-known problem with standard Future libraries: they are designed in such a way that they are not referentially transparent, as they readily evaluate and remember their result. In most cases, this is completely normal, and Scala developers rarely have to create the future without appreciation.

Run the following program:

 val x = Future(...); f(x, x) 

- this is not the same program as

 f(Future(...), Future(...)) 

because in the first case, the future is estimated once, in the second - twice.

These are libraries that provide the necessary abstractions for working with object-transparent asynchronous tasks, the evaluation of which is postponed and not stored in memory, unless explicitly required by the developer.

  • Scalaz challenge
  • Monix Challenge
  • fs2

If you want to use Cats, the effects of Cats work great with both Monix and fs2.

+1
source

Source: https://habr.com/ru/post/945103/


All Articles