Fix some longstanding string bugs and stop cheating with read-string in standard_grammer, implementing both unescape and string-to-int in k'
This commit is contained in:
24
k_prime.krak
24
k_prime.krak
@@ -692,13 +692,17 @@ fun main(argc: int, argv: **char): int {
|
||||
grammar.add_to_nonterminal(optional_WS, vec(WS), kpNil(), ret_nil_sym)
|
||||
|
||||
var atom = grammar.add_new_nonterminal("atom", vec(grammar.add_terminal("-?[0-9]+", kpNil(), fun(_: ref KPValue, input: ref str, l: int, r: int): KPResult { return KPResult::Ok(kpInt(string_to_num<int>(input.slice(l,r)))); })), kpNil(), ret_0_sym)
|
||||
grammar.add_to_nonterminal(atom, vec(grammar.add_terminal("\"([#-[]| |[]-~]|(\\\\)|(\\n)|(\\t)|(\\\*)|(\\0)|
|
||||
grammar.add_to_nonterminal(atom, vec(grammar.add_terminal("\"([#-[]| |[]-~]|(\\\\\\\\)|(\\\\n)|(\\\\t)|(\\*)|(\\\\0)|
|
||||
|[ -!]|(\\\\\"))*\"", kpNil(), fun(_: ref KPValue, input: ref str, l: int, r: int): KPResult { //"
|
||||
var to_ret = str()
|
||||
for (var i = l+1; i < r-1; i++;) {
|
||||
if input[i] == '\\' {
|
||||
if input[i+1] == 'n' {
|
||||
to_ret += '\n'
|
||||
} else if input[i+1] == 't' {
|
||||
to_ret += '\t'
|
||||
} else if input[i+1] == '0' {
|
||||
to_ret += '\0'
|
||||
} else if input[i+1] == '\\' || input[i+1] == '"' {
|
||||
to_ret += input[i+1]
|
||||
} else {
|
||||
@@ -846,6 +850,16 @@ fun main(argc: int, argv: **char): int {
|
||||
return make_pair(null<KPEnv>(), KPResult::Ok(kpBool(params[0].is_symbol())))
|
||||
}));
|
||||
|
||||
env->set(str("str-to-symbol"), make_builtin_combiner(str("str-to-symbol"), 1, false, fun(params: vec<KPValue>, dynamic_env: *KPEnv): pair<*KPEnv, KPResult> {
|
||||
if params.size != 1 {
|
||||
return make_pair(null<KPEnv>(), KPResult::Err(kpString(str("Need 1 param to str-to-symbol"))))
|
||||
}
|
||||
if !params[0].is_string() {
|
||||
return make_pair(null<KPEnv>(), KPResult::Err(kpString(str("Called get-text with not a symbol"))))
|
||||
}
|
||||
return make_pair(null<KPEnv>(), KPResult::Ok(kpSymbol(params[0].get_string())))
|
||||
}));
|
||||
|
||||
env->set(str("get-text"), make_builtin_combiner(str("get-text"), 1, false, fun(params: vec<KPValue>, dynamic_env: *KPEnv): pair<*KPEnv, KPResult> {
|
||||
if params.size != 1 {
|
||||
return make_pair(null<KPEnv>(), KPResult::Err(kpString(str("Need 1 param to get-text"))))
|
||||
@@ -893,7 +907,7 @@ fun main(argc: int, argv: **char): int {
|
||||
if params.size != 2 {
|
||||
return make_pair(null<KPEnv>(), KPResult::Err(kpString(str("Need 2 params to idx"))))
|
||||
}
|
||||
if !params[0].is_array() { return make_pair(null<KPEnv>(), KPResult::Err(kpString(str("Param 1 to idx is not array") + pr_str(params[0], true)))); }
|
||||
if !params[0].is_array() && !params[0].is_string() { return make_pair(null<KPEnv>(), KPResult::Err(kpString(str("Param 1 to idx is not string or array") + pr_str(params[0], true)))); }
|
||||
if !params[1].is_int() { return make_pair(null<KPEnv>(), KPResult::Err(kpString(str("Param 2 to idx is not int")))); }
|
||||
|
||||
var index = params[1].get_int()
|
||||
@@ -901,7 +915,11 @@ fun main(argc: int, argv: **char): int {
|
||||
index += params[0].get_array_rc().get().size
|
||||
}
|
||||
|
||||
if params[0].is_array() {
|
||||
return make_pair(null<KPEnv>(), KPResult::Ok(params[0].get_array_rc().get()[index]))
|
||||
} else {
|
||||
return make_pair(null<KPEnv>(), KPResult::Ok(kpInt((params[0].get_string()[index]) cast int)))
|
||||
}
|
||||
}));
|
||||
env->set(str("set-idx!"), make_builtin_combiner(str("set-idx!"), 1, false, fun(params: vec<KPValue>, dynamic_env: *KPEnv): pair<*KPEnv, KPResult> {
|
||||
if params.size != 3 {
|
||||
@@ -949,7 +967,7 @@ fun main(argc: int, argv: **char): int {
|
||||
for (var i = 0; i < params.size; i++;) {
|
||||
match (params[i].internal) {
|
||||
KPValue_int::Int(v) {
|
||||
if i == 0 {
|
||||
if i == 0 && params.size > 1 {
|
||||
to_ret += v
|
||||
} else {
|
||||
to_ret -= v
|
||||
|
||||
35
prelude.kp
35
prelude.kp
@@ -149,6 +149,33 @@
|
||||
print_through
|
||||
)
|
||||
insert_into_scope_let (lambda (scope_let name item) (array (idx scope_let 0) (concat (idx scope_let 1) (array name (array quote item)))))
|
||||
string-to-int (lambda (s) (let (
|
||||
helper (rec-lambda recurse (s i result)
|
||||
(if (< i (len s))
|
||||
(recurse s (+ i 1) (+ (* 10 result) (- (idx s i) (idx "0" 0))))
|
||||
result
|
||||
)
|
||||
))
|
||||
(if (= (idx s 0) (idx "-" 0))
|
||||
(- (helper s 1 0))
|
||||
(helper s 0 0)
|
||||
)))
|
||||
|
||||
unescape-str (lambda (s) (let (
|
||||
helper (rec-lambda recurse (s i r)
|
||||
(cond (>= (+ 1 i) (len s)) r
|
||||
(= (idx s i) (idx "\\" 0)) (cond (= (+ i 1) (len s)) "BAD ESCAPE AT END"
|
||||
(= (idx s (+ i 1)) (idx "n" 0)) (recurse s (+ i 2) (str r "\n"))
|
||||
(= (idx s (+ i 1)) (idx "t" 0)) (recurse s (+ i 2) (str r "\t"))
|
||||
(= (idx s (+ i 1)) (idx "0" 0)) (recurse s (+ i 2) (str r "\0"))
|
||||
(= (idx s (+ i 1)) (idx "\\" 0)) (recurse s (+ i 2) (str r "\\"))
|
||||
(= (idx s (+ i 1)) (idx "\"" 0)) (recurse s (+ i 2) (str r "\""))
|
||||
true "BAD ESCAPE IS NORMAL CHAR"
|
||||
)
|
||||
true (recurse s (+ i 1) (str r (slice s i (+ i 1))))
|
||||
)
|
||||
)) (helper s 1 "")))
|
||||
|
||||
scope_let (let-vrec (
|
||||
with_import (vau de (lib_path code)
|
||||
(let (imported_scope_let (eval (concat
|
||||
@@ -161,13 +188,13 @@
|
||||
(array (quote WS) (array "( | |
|
||||
|(;[ -~]*
|
||||
))+") (lambda (x) nil))
|
||||
(array (quote atom) (array "-?[0-9]+") (lambda (x) (do (println "read-str for number") (read-string x))))
|
||||
(array (quote atom) (array "\"([#-[]| |[]-~]|(\\\\)|(\\n)|(\\t)|(\\\\*)|(\\0)|
|
||||
|[ -!]|(\\\\\"))*\"") (lambda (x) (do (println "read-str for string") (read-string x))))
|
||||
(array (quote atom) (array "-?[0-9]+") (lambda (x) (string-to-int x)))
|
||||
(array (quote atom) (array "\"([#-[]| |[]-~]|(\\\\\\\\)|(\\\\n)|(\\\\t)|(\\*)|(\\\\0)|
|
||||
|[ -!]|(\\\\\"))*\"") (lambda (x) (unescape-str x)))
|
||||
(array (quote atom) (array "-|(([a-z]|[A-Z]|_|\\*|/|\\?|\\+|!|=|&|<|>|%)([a-z]|[A-Z]|_|[0-9]|\\*|\\?|\\+|-|!|=|&|<|>|%)*)") (lambda (x) (cond (= "true" x) true
|
||||
(= "false" x) false
|
||||
(= "nil" x) nil
|
||||
true (do (println "read-string for atom") (read-string x)))))
|
||||
true (str-to-symbol x))))
|
||||
(array (quote form) (array (quote atom)) (lambda (x) x))
|
||||
(array (quote form) (array "\\(" (quote WS) * "\\)" ) (lambda (_ _ _) (array)))
|
||||
(array (quote form) (array "\\(" (quote WS) * (quote form) (array (quote WS) + (quote form)) * (quote WS) * "\\)" ) (lambda (_ _ head tail _ _) (concat (array head) (map (lambda (x) (idx x 1)) tail))))
|
||||
|
||||
Reference in New Issue
Block a user