add shortcuts for quasiquote and unquote

This commit is contained in:
Pekka Laiho 2020-12-05 17:38:42 +07:00
parent a2f5cdbcc0
commit f1c49009ab
2 changed files with 16 additions and 7 deletions

View File

@ -16,12 +16,11 @@ class Reader
private function readForm(array $tokens, int &$index) private function readForm(array $tokens, int &$index)
{ {
if ($tokens[$index] == "'") { if ($tokens[$index] == "'") {
$index++; return $this->readSpecialForm($tokens, $index, 'quote');
$contents = [new Symbol('quote')]; } elseif ($tokens[$index] == "`") {
if ($index < count($tokens) && !in_array($tokens[$index], [')', ']', '}'])) { return $this->readSpecialForm($tokens, $index, 'quasiquote');
$contents[] = $this->readForm($tokens, $index); } elseif ($tokens[$index] == "~") {
} return $this->readSpecialForm($tokens, $index, 'unquote');
return new MList($contents);
} elseif ($tokens[$index] == '(') { } elseif ($tokens[$index] == '(') {
return $this->readList($tokens, $index); return $this->readList($tokens, $index);
} elseif ($tokens[$index] == '[') { } elseif ($tokens[$index] == '[') {
@ -33,6 +32,16 @@ class Reader
} }
} }
private function readSpecialForm(array $tokens, int &$index, string $symbol)
{
$index++;
$contents = [new Symbol($symbol)];
if ($index < count($tokens) && !in_array($tokens[$index], [')', ']', '}'])) {
$contents[] = $this->readForm($tokens, $index);
}
return new MList($contents);
}
private function readList(array $tokens, int &$index): MList private function readList(array $tokens, int &$index): MList
{ {
return new MList($this->readCollection($tokens, $index, ')')); return new MList($this->readCollection($tokens, $index, ')'));

View File

@ -69,7 +69,7 @@ class Tokenizer
$addCurrent(); $addCurrent();
$tokens[] = $c; $tokens[] = $c;
$parens[$parenIndexes[$c]]--; $parens[$parenIndexes[$c]]--;
} elseif ($c == "'") { } elseif ($c == "'" || $c == "`" || $c == "~") {
// Other special characters // Other special characters
$addCurrent(); $addCurrent();
$tokens[] = $c; $tokens[] = $c;