Created
December 11, 2018 19:53
-
-
Save mfelsche/a987e67f6ae804cc256a47736704f459 to your computer and use it in GitHub Desktop.
first function for promises - returning the first fulfilled value
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
use "promises" | |
use "collections" | |
actor _Selector[A: Any #share] | |
var _completed: Bool = false | |
var _outstanding: USize | |
let _promise: Promise[A] | |
new create(promise: Promise[A], expected: USize) => | |
_promise = promise | |
_outstanding = expected | |
be fulfill(a: A) => | |
if not _completed then | |
_promise(a) | |
_completed = true | |
end | |
_outstanding = _outstanding - 1 | |
be reject() => | |
if (_outstanding == 1) and not _completed then | |
// no promise was fulfilled | |
_promise.reject() | |
end | |
_outstanding = _outstanding - 1 | |
primitive PromisesExt | |
fun first[A: Any #share](promises: ReadSeq[Promise[A]]): Promise[A] => | |
""" | |
returns a promise which is fulfilled with the value of the first fulfilled promise from the given promises, | |
all other fulfilled or rejected promises are ignored. | |
If all promises got rejected, the returned promise is also rejected. | |
The returned promise will never be fulfilled if the given ReadSeq promises is empty. | |
""" | |
let select_p = Promise[A] | |
let selector = _Selector[A](select_p, promises.size()) | |
for promise in promises.values() do | |
promise.next[None]( | |
recover {(a) => selector.fulfill(a) } end, | |
recover {() => selector.reject() } end) | |
end | |
select_p | |
actor Main | |
new create(env: Env) => | |
let ps = Array[Promise[String]](10) | |
for x in Range(0, 10) do | |
ps.push(Promise[String]) | |
end | |
let p = PromisesExt.first[String](ps) | |
p.next[None]({(s) => env.out.print(s) }) | |
try | |
for x in Range(0, 10) do | |
ps(x)?(x.string()) | |
end | |
else | |
env.exitcode(1) | |
end |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment