Skip to content

Commit

Permalink
Add floats and booleans to Stdlib
Browse files Browse the repository at this point in the history
Literally just supports parsing floats and booleans from strings at the moment.
  • Loading branch information
JasonSteving99 committed Nov 18, 2023
1 parent 94fae8e commit 330bca1
Show file tree
Hide file tree
Showing 9 changed files with 120 additions and 0 deletions.
2 changes: 2 additions & 0 deletions src/java/com/claro/claro_build_rules_internal.bzl
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,9 @@ CLARO_STDLIB_FILES = [
# The names of these modules are going to be considered "reserved", so that language-wide users can become accustomed
# to these scopes being available (even if I decide to allow overriding stdlib dep modules in the future).
CLARO_STDLIB_MODULES = {
"booleans": "@claro-lang//stdlib/booleans:booleans",
"files": "@claro-lang//stdlib/files:files",
"floats": "@claro-lang//stdlib/floats:floats",
"futures": "@claro-lang//stdlib/futures:futures",
"ints": "@claro-lang//stdlib/ints:ints",
"lists": "@claro-lang//stdlib/lists:lists",
Expand Down
18 changes: 18 additions & 0 deletions stdlib/booleans/BUILD
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
load(
"//src/java/com/claro:claro_build_rules_internal.bzl",
"bootstrapped_claro_module_internal",
)
load("//:rules.bzl", "claro_binary")

bootstrapped_claro_module_internal(
name = "booleans",
module_api_file = "booleans.claro_module_api",
srcs = ["booleans.claro_internal"],
visibility = ["//visibility:public"],
)


claro_binary(
name = "test",
main_file = "test.claro",
)
8 changes: 8 additions & 0 deletions stdlib/booleans/booleans.claro_internal
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@

function parseBoolean(s: string) -> boolean {
var res: boolean;
$$BEGIN_JAVA
res = java.lang.Boolean.parseBoolean(s);
$$END_JAVA
return res;
}
2 changes: 2 additions & 0 deletions stdlib/booleans/booleans.claro_module_api
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@

function parseBoolean(s: string) -> boolean;
6 changes: 6 additions & 0 deletions stdlib/booleans/test.claro
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@

var tests = ["true", "false", "True", "yes", "no"];
for (test in tests) {
var parsed = booleans::parseBoolean(test);
print("booleans::parseBoolean(\"{test}\") == {parsed}");
}
23 changes: 23 additions & 0 deletions stdlib/floats/BUILD
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
load(
"//src/java/com/claro:claro_build_rules_internal.bzl",
"bootstrapped_claro_module_internal",
"CLARO_STDLIB_MODULES",
)
load("//:rules.bzl", "claro_binary")

bootstrapped_claro_module_internal(
name = "floats",
module_api_file = "floats.claro_module_api",
srcs = ["floats.claro_internal"],
deps = {
"std": CLARO_STDLIB_MODULES["std"],
},
exports = ["std"],
visibility = ["//visibility:public"],
)


claro_binary(
name = "test",
main_file = "test.claro",
)
15 changes: 15 additions & 0 deletions stdlib/floats/floats.claro_internal
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@

function parseFloat(s: string) -> oneof<float, std::Error<InvalidNumberFormat>> {
var res: oneof<float, std::Error<InvalidNumberFormat>>;

var errCons = (msg: string) -> std::Error<InvalidNumberFormat> { return std::Error(InvalidNumberFormat({msg = msg})); };

$$BEGIN_JAVA
try {
res = java.lang.Double.parseDouble(s);
} catch (java.lang.NumberFormatException e) {
res = errCons.apply(e.getMessage());
}
$$END_JAVA
return res;
}
4 changes: 4 additions & 0 deletions stdlib/floats/floats.claro_module_api
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@

newtype InvalidNumberFormat : struct { msg: string }

function parseFloat(s: string) -> oneof<float, std::Error<InvalidNumberFormat>>;
42 changes: 42 additions & 0 deletions stdlib/floats/test.claro
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@

match (floats::parseFloat(input("Give me a float to try parsing:"))) {
case parsed:float -> print("Successfully parsed the given float: {parsed}");
case ERR -> print("Failed to parse: {ERR}");
}

print("Let's simulate a shitty calculator that can only do addition or subtraction of two terms...");
var inputExpr = input("Give me a single addition expression (e.g.: 1 + 1):");

atom ADD
atom SUBTRACT
newtype Expr : struct {
lhs : float,
op: oneof<ADD, SUBTRACT>,
rhs : float
}

var tokens = strings::split(inputExpr, " ");
if (len(tokens) == 3) {
var expr: oneof<Expr, std::Error<string>>;
match ((floats::parseFloat(tokens[0]), tokens[1], floats::parseFloat(tokens[2]))) {
case (lhs:float, "+", rhs:float) ->
expr = Expr({lhs = lhs, op = ADD, rhs = rhs});
case (lhs:float, "-", rhs:float) ->
expr = Expr({lhs = lhs, op = SUBTRACT, rhs = rhs});
case _ ->
expr = std::Error("Error! Expected Expr in the format: <float> <+|-> <float>");
}
match (expr) {
case ERR:std::Error<string> ->
print(unwrap(ERR));
case _:Expr ->
match (unwrap(expr)) {
case {lhs = lhs, op = _:ADD, rhs = rhs} ->
print("= {lhs + rhs}");
case {lhs = lhs, op = _:SUBTRACT, rhs = rhs} ->
print("= {lhs - rhs}");
}
}
} else {
print("Error! Expected 3 tokens separated by whitespace!");
}

0 comments on commit 330bca1

Please sign in to comment.