aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAdrian Kummerlaender2017-04-15 18:16:39 +0200
committerAdrian Kummerlaender2017-04-15 18:16:39 +0200
commit568e457d5f879633adc8a33d8c2979d563556868 (patch)
tree1c5ec482edb0c6643b32278a2eb2e31a37dfa734
parentbce4d934a47023096e74ac39ed4d3a2cd99bc8e4 (diff)
downloadslang-568e457d5f879633adc8a33d8c2979d563556868.tar
slang-568e457d5f879633adc8a33d8c2979d563556868.tar.gz
slang-568e457d5f879633adc8a33d8c2979d563556868.tar.bz2
slang-568e457d5f879633adc8a33d8c2979d563556868.tar.lz
slang-568e457d5f879633adc8a33d8c2979d563556868.tar.xz
slang-568e457d5f879633adc8a33d8c2979d563556868.tar.zst
slang-568e457d5f879633adc8a33d8c2979d563556868.zip
Handle definition, conditional primitive words in respective modules
-rw-r--r--source/base/definition.d47
-rw-r--r--source/primitives/conditional.d60
-rw-r--r--source/primitives/core.d5
-rw-r--r--source/primitives/eval.d4
4 files changed, 64 insertions, 52 deletions
diff --git a/source/base/definition.d b/source/base/definition.d
index cf64f3e..4c0f50c 100644
--- a/source/base/definition.d
+++ b/source/base/definition.d
@@ -13,11 +13,7 @@ alias Words = Stack!Token[string];
Nullable!(DList!Token) definition;
Words words;
-void start() {
- definition = DList!Token();
-}
-
-void end() {
+void register(DList!Token definition) {
string wordToBeDefined;
definition.front.visit!(
@@ -32,27 +28,48 @@ void end() {
definition.removeFront;
words[wordToBeDefined] = Stack!Token(definition[]);
- definition.nullify;
}
-bool handle(Token token) {
+template handle(T)
+if ( is(T == int) || is(T == bool) ) {
+ bool handle(T value) {
+ if ( definition.isNull ) {
+ return false;
+ } else {
+ definition.insertBack(Token(value));
+ return true;
+ }
+ }
+}
+
+bool handle(string word) {
if ( definition.isNull ) {
- return false;
+ if ( word == "§" ) {
+ definition = DList!Token();
+ return true;
+ } else {
+ return false;
+ }
} else {
- if ( token.type == typeid(string) ) {
- if ( *token.peek!string == ";" ) {
- end;
- } else {
- definition.insertBack(token);
- }
+ if ( word == ";" ) {
+ register(definition);
+ definition.nullify;
} else {
- definition.insertBack(token);
+ definition.insertBack(Token(word));
}
return true;
}
}
+bool handle(Token token) {
+ return token.visit!(
+ (int value) => handle(value),
+ (bool value) => handle(value),
+ (string word ) => handle(word)
+ );
+}
+
Stack!Token get(string word) {
if ( word in words ) {
return words[word].dup;
diff --git a/source/primitives/conditional.d b/source/primitives/conditional.d
index e5ba591..38f0050 100644
--- a/source/primitives/conditional.d
+++ b/source/primitives/conditional.d
@@ -10,32 +10,7 @@ Nullable!(DList!Token) buffer;
bool concluded = true;
bool drop_mode = false;
-void capture(Token token) {
- if ( !drop_mode ) {
- buffer.insertBack(token);
- }
-}
-
-bool handle(Token token) {
- if ( concluded && buffer.isNull ) {
- return false;
- }
-
- if ( token.type == typeid(string) ) {
- switch ( *token.peek!string ) {
- case "if" : eval_if; break;
- case "then" : eval_then; break;
- case "else" : eval_else; break;
- default : capture(token); break;
- }
- } else {
- capture(token);
- }
-
- return true;
-}
-
-void eval_if() {
+void unary_op_if() {
if ( concluded ) {
buffer = DList!Token();
drop_mode = !stack.pop.get!bool;
@@ -45,7 +20,7 @@ void eval_if() {
}
}
-void eval_then() {
+void n_ary_op_then() {
if ( concluded ) {
throw new Exception("`then` without preceding `if`");
} else {
@@ -53,7 +28,7 @@ void eval_then() {
}
}
-void eval_else() {
+void n_ary_op_else() {
if ( concluded ) {
throw new Exception("`else` without preceding `if`");
} else {
@@ -62,6 +37,35 @@ void eval_else() {
}
}
+bool capture(Token token) {
+ if ( concluded && buffer.isNull ) {
+ return false;
+ } else {
+ if ( !drop_mode ) {
+ buffer.insertBack(token);
+ }
+
+ return true;
+ }
+}
+
+bool handle(string word) {
+ switch ( word ) {
+ case "if" : unary_op_if; return true;
+ case "then" : n_ary_op_then; return true;
+ case "else" : n_ary_op_else; return true;
+ default : return capture(Token(word));
+ }
+}
+
+bool handle(Token token) {
+ return token.visit!(
+ (int ) => capture(token),
+ (bool ) => capture(token),
+ (string word) => handle(word)
+ );
+}
+
bool dischargeable() {
return concluded && !buffer.isNull;
}
diff --git a/source/primitives/core.d b/source/primitives/core.d
index 45bbeac..07ed0c7 100644
--- a/source/primitives/core.d
+++ b/source/primitives/core.d
@@ -3,14 +3,9 @@ module primitives.core;
import std.stdio;
import base.stack;
-import definition = base.definition;
Token[string] variables;
-void definition_start() {
- definition.start;
-}
-
void binary_op_variable_bind() {
string name = stack.pop.get!string;
Token value = stack.pop;
diff --git a/source/primitives/eval.d b/source/primitives/eval.d
index 0cb45b7..2ae5373 100644
--- a/source/primitives/eval.d
+++ b/source/primitives/eval.d
@@ -10,12 +10,8 @@ import conditional = primitives.conditional;
bool evaluate_primitive(string word) {
switch ( word ) {
- case "§" : definition_start; break;
case "$" : binary_op_variable_bind; break;
case "@" : unary_op_variable_resolve; break;
- case "if" : conditional.eval_if; break;
- case "then" : conditional.eval_then; break;
- case "else" : conditional.eval_else; break;
case "+" : binary_op_add; break;
case "*" : binary_op_multiply; break;
case "/" : binary_op_divide; break;