Promise represents a value that will be available at a later time.
Promises can either be fulfilled with a value or rejected. Any number of function handlers can be added to the
Promise, to be called when the
Promise is fulfilled or rejected. These handlers themselves are also wrapped in
Promises so that they can be chained together in order for the fulfilled value of one
Promise to be used to compute a value which will be used to fulfill the next
Promise in the chain, or so that if the
Promise is rejected then the subsequent reject functions will also be called. The input and output types of a fulfill handler do not have to be the same, so a chain of fulfill handlers can transform the original value into something new.
Fulfill and reject handlers can either be specified as classes that implment the
Reject interfaces, or as functions with the same signatures as the
apply methods in
In the following code, the fulfillment of the
Promise causes the execution of several fulfillment functions. The output is:
fulfilled + foo fulfilled + bar fulfilled + baz
use "promises" class PrintFulfill is Fulfill[String, String] let _env: Env let _msg: String new create(env: Env, msg: String) => _env = env _msg = msg fun apply(s: String): String => _env.out.print(" + ".join([s; _msg].values())) s actor Main new create(env: Env) => let promise = Promise[String] promise.next[String](recover PrintFulfill(env, "foo") end) promise.next[String](recover PrintFulfill(env, "bar") end) promise.next[String](recover PrintFulfill(env, "baz") end) promise("fulfilled")
In the following code, the fulfill functions are chained together so that the fulfilled value of the first one is used to generate a value which fulfills the second one, which in turn is used to compute a value which fulfills the third one, which in turn is used to compute a value which fulfills the fourth one. The output is the average length of the words passed on the command line or
0 if there are no command line arguments.
use "promises" primitive Computation fun tag string_to_strings(s: String): Array[String] val => recover s.split() end fun tag strings_to_sizes(sa: Array[String] val): Array[USize] val => recover let len = Array[USize] for s in sa.values() do len.push(s.size()) end len end fun tag sizes_to_avg(sza: Array[USize] val): USize => var acc = USize(0) for sz in sza.values() do acc = acc + sz end acc / sza.size() fun tag output(env: Env, sz: USize): None => env.out.print(sz.string()) actor Main new create(env: Env) => let promise = Promise[String] promise.next[Array[String] val](recover Computation~string_to_strings() end) .next[Array[USize] val](recover Computation~strings_to_sizes() end) .next[USize](recover Computation~sizes_to_avg() end) .next[None](recover Computation~output(env) end) promise(" ".join(env.args.slice(1).values()))
© 2016-2018, The Pony Developers
© 2014-2015, Causality Ltd.
Licensed under the BSD 2-Clause License.