Arc Forumnew | comments | leaders | submitlogin
Semi-Arc with first-class continuations (
3 points by suzuki 1484 days ago | 3 comments

3 points by suzuki 1483 days ago | link

This arc seems faster than rainbow in start-up, but slower in execution. On MacBook Air 2019, for N-queens puzzle (N = 9 and 11),

  $ time java -jar arc.jar ~/tmp/arc-in-java-0.2.0/9queens.arc 
  real	0m1.634s
  user	0m3.056s
  sys	0m0.159s

  $ time java -jar arc.jar ~/tmp/11queens.arc 

  real	0m27.865s
  user	0m29.582s
  sys	0m0.242s

  $ time java -jar rainbow.jar -q -f ~/tmp/arc-in-java-0.2.0/9queens.arc 
  *** redefining no
  *** redefining map1
  *** redefining pr
  *** redefining list
  real	0m2.279s
  user	0m6.492s
  sys	0m0.246s

  $ time java -jar rainbow.jar -q -f ~/tmp/11queens.arc 
  *** redefining no
  *** redefining map1
  *** redefining pr
  *** redefining list
  real	0m9.812s
  user	0m14.462s
  sys	0m0.360s

  $ java -version
  openjdk version "11.0.7" 2020-04-14
  OpenJDK Runtime Environment AdoptOpenJDK (build 11.0.7+10)
  OpenJDK 64-Bit Server VM AdoptOpenJDK (build 11.0.7+10, mixed mode)
As for the code size, this arc's arc folder has 4,626 lines of Java 11 while rainbow's src/java/rainbow folder has 14,520 lines (72,190 lines including auto-generated ones) of Java 5.

In short, this arc is a small-scale implementation of Arc.


2 points by rocketnia 1482 days ago | link

It's great to see you again! Sometimes I've wondered about the status of Semi-Arc. Looks like you've been working on a number of other Lisp implementations in the meantime! Pretty exciting. Thanks for sharing this update with us.

As someone who ported Rainbow line by line to JavaScript, I have to say, the size of the codebase can be quite daunting. A smaller implementation sounds a lot easier to work on.


5 points by suzuki 1482 days ago | link

It is my pleasure.

As I referred in, the implementation of this arc's continuations is based on If you are planning to port this arc to JavaScript, I suggest reading which implements the continuations in the same way in TypeScript.

And in the latter, the display function

  c('display', 1, x => {
      write(stringify(fst(x), false));
      return new Promise(resolve => {
          runOnNextLoop(() => resolve(None));
is applied asynchronously, in a sense, as follows:

  case ContOp.ApplyFun: // exp2 is a function.
      [exp, env] = applyFunction(exp2, args, k, env);
      if (exp instanceof Promise)
          exp = await exp;
This means the web page is still interactive during the evaluation effectively. Here is an example: Click the "Load" button twice and you will see two "yin-yang puzzle" threads run on the page. Click the "Stop at Writing" button twice to stop them.