Warning: session_start(): open(/var/lib/php/sessions/sess_iaf8hjn1macvvgl57c97hmno0i, O_RDWR) failed: No space left on device (28) in /var/www/tb-usercake/models/config.php on line 51
Warning: session_start(): Failed to read session data: files (path: /var/lib/php/sessions) in /var/www/tb-usercake/models/config.php on line 51
sclass VStack is Steppable, IVStack {
new L stack;
O latestResult;
transient O newResult;
// the null sentinel replaces a null function result
// when stored in latestResult
sclass NullSentinel {}
static new NullSentinel nullSentinel;
*() {}
*(Computable computation) { push(computation); }
*(Iterable l) { pushAll(l); }
// A is what the function returns
interface Computable {
public void step(VStack stack, O subComputationResult);
}
private O deSentinel(O o) {
ret o instanceof NullSentinel ? null : o;
}
private O sentinel(O o) {
ret o == null ? nullSentinel : o;
}
// called by computations or users to start a subroutine
public void push(Computable computation) {
stack.add(computation);
}
// perform a computation step. returns false iff done
public bool step() {
if (empty(stack)) false;
newResult = null;
last(stack).step(this, result());
latestResult = newResult;
newResult = null;
true;
}
// called from a computation to return a value
public void _return(O value) {
newResult = sentinel(value);
removeLast(stack);
}
// called from a computation to tail-call another routine
void tailCall aka replace(Computable computation) {
removeLast(stack);
stack.add(computation);
}
// all-in-one evaluation function - call on an empty stack
A compute(Computable computation) {
if (computation == null) null;
push(computation);
stepAll(this);
ret (A) latestResult;
}
// return result of just completed computation or sub-computation
O result aka subResult() {
ret deSentinel(latestResult);
}
bool hasSubResult() { ret latestResult != null; }
void pushAll(Iterable l) {
fOr (Computable c : l)
push(c);
}
void add(Runnable r) {
if (r == null) ret;
push((stack, subComputationResult) -> r.run());
}
// caller of current function
Computable caller() {
ret nextToLast(stack);
}
}