mirror of
https://github.com/peklaiho/madlisp.git
synced 2024-11-22 13:24:46 +00:00
add support for userfuncs to meta
This commit is contained in:
parent
5bb2b458b3
commit
1ece3649bc
@ -159,7 +159,7 @@ class Evaller
|
||||
return $this->eval($astData[2], $newEnv);
|
||||
};
|
||||
|
||||
return new UserFunc($closure, $astData[2], $env, $bindings);
|
||||
return new UserFunc($closure, $astData[2], $env, $astData[1]);
|
||||
} elseif ($symbolName == 'if') {
|
||||
if ($astLength < 3 || $astLength > 4) {
|
||||
throw new MadLispException("if requires 2 or 3 arguments");
|
||||
|
@ -47,6 +47,16 @@ class LispFactory
|
||||
} else {
|
||||
throw new MadLispException('unknown attribute for meta');
|
||||
}
|
||||
} elseif ($obj instanceof UserFunc) {
|
||||
if ($attribute == 'args') {
|
||||
return $obj->getBindings();
|
||||
} elseif ($attribute == 'body') {
|
||||
return $obj->getAst();
|
||||
} elseif ($attribute == 'code') {
|
||||
return new MList([new Symbol('fn'), $obj->getBindings(), $obj->getAst()]);
|
||||
} else {
|
||||
throw new MadLispException('unknown attribute for meta');
|
||||
}
|
||||
} else {
|
||||
throw new MadLispException('unknown entity for meta');
|
||||
}
|
||||
@ -71,7 +81,7 @@ class LispFactory
|
||||
));
|
||||
|
||||
$env->set('exit', new CoreFunc('exit', 'Terminate the script with given exit code.', 0, 1,
|
||||
function ($status = 0) {
|
||||
function (int $status = 0) {
|
||||
exit($status);
|
||||
}
|
||||
));
|
||||
|
@ -7,9 +7,9 @@ class UserFunc extends Func
|
||||
{
|
||||
protected $ast;
|
||||
protected Env $tempEnv;
|
||||
protected array $bindings;
|
||||
protected Seq $bindings;
|
||||
|
||||
public function __construct(Closure $closure, $ast, Env $tempEnv, array $bindings)
|
||||
public function __construct(Closure $closure, $ast, Env $tempEnv, Seq $bindings)
|
||||
{
|
||||
parent::__construct($closure, null);
|
||||
|
||||
@ -23,12 +23,18 @@ class UserFunc extends Func
|
||||
return $this->ast;
|
||||
}
|
||||
|
||||
public function getBindings(): Seq
|
||||
{
|
||||
return $this->bindings;
|
||||
}
|
||||
|
||||
public function getEnv(array $args)
|
||||
{
|
||||
$newEnv = new Env('apply', $this->tempEnv);
|
||||
|
||||
for ($i = 0; $i < count($this->bindings); $i++) {
|
||||
$newEnv->set($this->bindings[$i]->getName(), $args[$i] ?? null);
|
||||
$bindings = $this->bindings->getData();
|
||||
for ($i = 0; $i < count($bindings); $i++) {
|
||||
$newEnv->set($bindings[$i]->getName(), $args[$i] ?? null);
|
||||
}
|
||||
|
||||
return $newEnv;
|
||||
|
Loading…
Reference in New Issue
Block a user