Thu Apr 10 17:22:33 EDT 2008

conditional jumps

these are special.. but how exactly?

one of the things i'd like to try is to isolate loop bodies so they
can be optimized. the previous 'amb' based approach (for .. next) is a
bit of a dirty hack, and doesn't work very well with non-flat code as

the for..next opti checks to see which of these produces the smallest
loop body.

       for .. next
       dup for drop .. save next drop

so, what is the pattern here?
  * execute a couple of simultaneous paths
  * choose the best one

this probably needs a purely functional split loop, so continuations
can be used without trouble. let's try that.

what does 'split' do? it calls 'next' and then continues. so it needs
a true continuation.


  * split doesn't need call/cc: it just produces a value, and that
    value isn't all that interesting.

  * in the loop body, no assignments can be made: when a split occurs,
    just cons the word and code list together, and perform mutation
    AFTER everything is done.

OK, i think i got it written down.. not sure whether it will work
though: afraid that the continuations in the macro evaluation will
somehow interfere with the update loop..

it should really be seen as 2 tasks communicating.. anyhow. more

i can't get this to work.. probably i'm discarding things i'm
collecting when calling the continuation. maybe composable
continuations work here? but i don't really understand them yet.. it's
like stuff pushed to the return stack..

so why can't this be solved in a monadic way? actually, this is the
same problem as the one i'm trying to solve with passing data
alongside the normal stack: because there's no room besides 'data' i
can't just tuck away more stuff..

looks like this is getting me closer to how to implement the core
mechanism for monadic threading... probably going to learn a thing or
two here. let's concentrate.

  - a macro is a map  (stack,asm) -> (stack,asm)

  - i'd like to extend this to a map (words,stack,asm) ->
    (words,stack,asm) which has a single mixing operator 'split', and
    all the other operations are lifted.

how to do this?


from plt manual:

  (reset val) => val
  (reset E[(shift k expr)]) => (reset ((lambda (k) expr)
                                       (lambda (v) (reset E[v]))))
    ; where E has no reset


  (prompt val) => val
  (prompt E[(control k expr)]) => (prompt ((lambda (k) expr)
                                          (lambda (v) E[v])))
    ; where E has no prompt

applied to the monadic bladibla: suppose 'D' performs some mixing with
other state y, but all the small caps operate only on x.

(lambda (x y)
  (a (b (c (D (e (f x)))))))


(lambda (x y)
            (shift abc
                   (let ((x+ (e (f x))))
                     (values (merge2 x+ y)
                             (abc (merge x+ y)))))))))))))

this way, the extra data 'y+' can be passed sideways, not going
through the 'abc' chain.

so.. as long as an expression is wrapped in a reset, 'shift' can get
inbetween. how to use this for implementing lifting? one prompt tag
per lifted thing?