Completely change naming conventions of field forms and definition macros. Close #32
This commit is contained in:
@@ -34,12 +34,9 @@ class CompileError {
|
||||
firstPos + '-' + lastPos.substr(justLineAndColumnIdx);
|
||||
}
|
||||
|
||||
var failed = if (warning) "warning!"; else "failed!";
|
||||
var failed = if (warning) "warning"; else "failed";
|
||||
|
||||
return '\nKiss compilation $failed\n'
|
||||
+ posPrefix
|
||||
+ ": "
|
||||
+ message
|
||||
return '$posPrefix: Kiss compilation $failed: $message'
|
||||
+ "\nFrom:"
|
||||
+ [for (exp in exps) exp.def.toString()].toString();
|
||||
}
|
||||
|
@@ -29,22 +29,22 @@ class FieldForms {
|
||||
map[newName] = form;
|
||||
}
|
||||
|
||||
map["defvar"] = varOrProperty.bind("classVar");
|
||||
renameAndDeprecate("defvar", "classVar");
|
||||
map["defprop"] = varOrProperty.bind("classProp");
|
||||
renameAndDeprecate("defprop", "classProp");
|
||||
map["defvar"] = varOrProperty.bind("var");
|
||||
renameAndDeprecate("defvar", "var");
|
||||
map["defprop"] = varOrProperty.bind("prop");
|
||||
renameAndDeprecate("defprop", "prop");
|
||||
|
||||
map["defun"] = funcOrMethod.bind("classFunction");
|
||||
renameAndDeprecate("defun", "classFunction");
|
||||
map["defmethod"] = funcOrMethod.bind("classMethod");
|
||||
renameAndDeprecate("defmethod", "classMethod");
|
||||
map["defun"] = funcOrMethod.bind("function");
|
||||
renameAndDeprecate("defun", "function");
|
||||
map["defmethod"] = funcOrMethod.bind("method");
|
||||
renameAndDeprecate("defmethod", "method");
|
||||
|
||||
return map;
|
||||
}
|
||||
|
||||
static function fieldAccess(formName:String, fieldName:String, nameExp:ReaderExp, ?access:Array<Access>) {
|
||||
if (access == null) {
|
||||
access = if (["defvar", "defprop", "classVar", "classProp"].indexOf(formName) != -1) {
|
||||
access = if (["defvar", "defprop", "var", "prop"].indexOf(formName) != -1) {
|
||||
[AFinal];
|
||||
} else {
|
||||
[];
|
||||
@@ -69,7 +69,7 @@ class FieldForms {
|
||||
access.push(AFinal);
|
||||
fieldAccess(formName, fieldName, nameExp, access);
|
||||
default:
|
||||
if (["defvar", "defun", "classVar", "classFunction"].indexOf(formName) != -1) {
|
||||
if (["defvar", "defun", "var", "function"].indexOf(formName) != -1) {
|
||||
access.push(AStatic);
|
||||
}
|
||||
access.push(if (fieldName.startsWith("_")) APrivate else APublic);
|
||||
|
@@ -340,7 +340,7 @@ class Macros {
|
||||
}
|
||||
|
||||
macros["defmacro"] = (wholeExp:ReaderExp, exps:Array<ReaderExp>, k:KissState) -> {
|
||||
wholeExp.checkNumArgs(3, null, '(defmacro [name] [[args...]] [body...])');
|
||||
wholeExp.checkNumArgs(3, null, '(defMacro [name] [[args...]] [body...])');
|
||||
|
||||
var name = switch (exps[0].def) {
|
||||
case Symbol(name): name;
|
||||
@@ -439,9 +439,10 @@ class Macros {
|
||||
|
||||
null;
|
||||
};
|
||||
renameAndDeprecate("defmacro", "defMacro");
|
||||
|
||||
macros["undefmacro"] = (wholeExp:ReaderExp, exps:Array<ReaderExp>, k:KissState) -> {
|
||||
wholeExp.checkNumArgs(1, 1, '(undefmacro [name])');
|
||||
wholeExp.checkNumArgs(1, 1, '(undefMacro [name])');
|
||||
|
||||
var name = switch (exps[0].def) {
|
||||
case Symbol(name): name;
|
||||
@@ -451,9 +452,10 @@ class Macros {
|
||||
k.macros.remove(name);
|
||||
null;
|
||||
};
|
||||
renameAndDeprecate("undefmacro", "undefMacro");
|
||||
|
||||
macros["defreadermacro"] = (wholeExp:ReaderExp, exps:Array<ReaderExp>, k:KissState) -> {
|
||||
wholeExp.checkNumArgs(3, null, '(defreadermacro [optional &start] ["[startingString]" or [startingStrings...]] [[streamArgName]] [body...])');
|
||||
wholeExp.checkNumArgs(3, null, '(defReaderMacro [optional &start] ["[startingString]" or [startingStrings...]] [[streamArgName]] [body...])');
|
||||
|
||||
// reader macros declared in the form (defreadermacro &start ...) will only be applied
|
||||
// at the beginning of lines
|
||||
@@ -464,9 +466,9 @@ class Macros {
|
||||
var strings = switch (exps[0].def) {
|
||||
case MetaExp("start", stringsExp):
|
||||
table = k.startOfLineReadTable;
|
||||
stringsThatMatch(stringsExp, "defreadermacro");
|
||||
stringsThatMatch(stringsExp, "defReaderMacro");
|
||||
default:
|
||||
stringsThatMatch(exps[0], "defreadermacro");
|
||||
stringsThatMatch(exps[0], "defReaderMacro");
|
||||
};
|
||||
for (s in strings) {
|
||||
switch (exps[1].def) {
|
||||
@@ -487,9 +489,10 @@ class Macros {
|
||||
|
||||
return null;
|
||||
};
|
||||
renameAndDeprecate("defreadermacro", "defReaderMacro");
|
||||
|
||||
macros["undefreadermacro"] = (wholeExp:ReaderExp, exps:Array<ReaderExp>, k:KissState) -> {
|
||||
wholeExp.checkNumArgs(1, 1, '(undefreadermacro [optional &start] ["[startingString]" or [startingStrings...]])');
|
||||
wholeExp.checkNumArgs(1, 1, '(undefReaderMacro [optional &start] ["[startingString]" or [startingStrings...]])');
|
||||
// reader macros undeclared in the form (undefreadermacro &start ...) will be removed from the table
|
||||
// for reader macros that must be at the beginning of lines
|
||||
// at the beginning of lines
|
||||
@@ -509,6 +512,7 @@ class Macros {
|
||||
}
|
||||
return null;
|
||||
};
|
||||
renameAndDeprecate("undefreadermacro", "undefReaderMacro");
|
||||
|
||||
// Having this floating out here is sketchy, but should work out fine because the variable is always re-set
|
||||
// through the next function before being used in defalias or undefalias
|
||||
@@ -535,20 +539,22 @@ class Macros {
|
||||
}
|
||||
|
||||
macros["defalias"] = (wholeExp:ReaderExp, exps:Array<ReaderExp>, k:KissState) -> {
|
||||
wholeExp.checkNumArgs(2, 2, "(defalias [[&call or &ident] whenItsThis] [makeItThis])");
|
||||
var name = getAliasName(k, exps[0], "defalias");
|
||||
wholeExp.checkNumArgs(2, 2, "(defAlias [[&call or &ident] whenItsThis] [makeItThis])");
|
||||
var name = getAliasName(k, exps[0], "defAlias");
|
||||
|
||||
aliasMap[name] = exps[1].def;
|
||||
return null;
|
||||
};
|
||||
renameAndDeprecate("defalias", "defAlias");
|
||||
|
||||
macros["undefalias"] = (wholeExp:ReaderExp, exps:Array<ReaderExp>, k:KissState) -> {
|
||||
wholeExp.checkNumArgs(1, 1, "(undefalias [[&call or &ident] alias])");
|
||||
var name = getAliasName(k, exps[0], "undefalias");
|
||||
wholeExp.checkNumArgs(1, 1, "(undefAlias [[&call or &ident] alias])");
|
||||
var name = getAliasName(k, exps[0], "undefAlias");
|
||||
|
||||
aliasMap.remove(name);
|
||||
return null;
|
||||
};
|
||||
renameAndDeprecate("undefalias", "undefAlias");
|
||||
|
||||
// Macros that null-check and extract patterns from enums (inspired by Rust)
|
||||
function ifLet(wholeExp:ReaderExp, exps:Array<ReaderExp>, k:KissState) {
|
||||
@@ -661,11 +667,11 @@ class Macros {
|
||||
|
||||
var propertyDefs = [for (bindingPair in bindingPairs) {
|
||||
var b = bindingPair[0].expBuilder();
|
||||
b.call(b.symbol("defprop"), [bindingPair[0]]);
|
||||
b.call(b.symbol("prop"), [bindingPair[0]]);
|
||||
}];
|
||||
var propertySetExps = [for (bindingPair in bindingPairs) {
|
||||
var b = bindingPair[1].expBuilder();
|
||||
b.call(b.symbol("set"), [b.symbol(Helpers.varName("a defprop property binding", bindingPair[0])), bindingPair[1]]);
|
||||
b.call(b.symbol("set"), [b.symbol(Helpers.varName("a prop property binding", bindingPair[0])), bindingPair[1]]);
|
||||
}];
|
||||
|
||||
var argList = [];
|
||||
@@ -676,7 +682,7 @@ class Macros {
|
||||
case MetaExp("prop", propExp):
|
||||
argList.push(propExp);
|
||||
propertyDefs.push(
|
||||
b.call(b.symbol("defprop"), [propExp]));
|
||||
b.call(b.symbol("prop"), [propExp]));
|
||||
// TODO allow &prop &mut or &mut &prop
|
||||
switch (propExp.def) {
|
||||
case TypedExp(_, {pos: _, def: Symbol(name)}):
|
||||
@@ -693,7 +699,7 @@ class Macros {
|
||||
var b = wholeExp.expBuilder();
|
||||
|
||||
return b.begin(propertyDefs.concat([
|
||||
b.call(b.symbol("defmethod"), [
|
||||
b.call(b.symbol("method"), [
|
||||
b.symbol("new"),
|
||||
b.list(argList)
|
||||
].concat(propertySetExps).concat(exps.slice(2)))
|
||||
@@ -715,8 +721,8 @@ class Macros {
|
||||
return b.call(b.symbol("when"), [flag, b.call(b.symbol("set"), [flag, b.symbol("false")])].concat(exps));
|
||||
}
|
||||
|
||||
macros["once"] = once.bind("defvar");
|
||||
macros["oncePerInstance"] = once.bind("defprop");
|
||||
macros["once"] = once.bind("var");
|
||||
macros["oncePerInstance"] = once.bind("prop");
|
||||
|
||||
// Replace "try" with this in a try-catch statement to let all exceptions throw
|
||||
// their original call stacks. This is more convenient for debugging than trying to
|
||||
|
@@ -226,7 +226,7 @@ class SpecialForms {
|
||||
case KeyValueExp(_, _): k.convert(namesExp);
|
||||
default: {
|
||||
bodyExps.insert(0,
|
||||
CallExp(Symbol("deflocal").withPosOf(args[2]), [namesExp, Symbol(uniqueVarName).withPosOf(args[2])]).withPosOf(args[2]));
|
||||
CallExp(Symbol("localVar").withPosOf(args[2]), [namesExp, Symbol(uniqueVarName).withPosOf(args[2])]).withPosOf(args[2]));
|
||||
macro $i{uniqueVarName};
|
||||
}
|
||||
};
|
||||
|
@@ -1,80 +1,80 @@
|
||||
// (load) brings in the fields and compile-time definitions of another Kiss file
|
||||
(load "BasicTestCaseExtra.kiss")
|
||||
|
||||
// (defvar) declares static variables
|
||||
(defvar message "Howdy")
|
||||
// (var) declares static variables
|
||||
(var message "Howdy")
|
||||
|
||||
// #| ... |# parses and injects raw Haxe code
|
||||
(defvar mathResult #|5 + 6 * 3|#) // Order of operations will apply
|
||||
(var mathResult #|5 + 6 * 3|#) // Order of operations will apply
|
||||
|
||||
// (defun) declares static functions
|
||||
(defun myFloor [num]
|
||||
// (function) declares static functions
|
||||
(function myFloor [num]
|
||||
// funcalls can use dot access
|
||||
(Math.floor num))
|
||||
|
||||
// functions are resolved in the macro context
|
||||
(defvar funResult (myFloor 7.5))
|
||||
(var funResult (myFloor 7.5))
|
||||
|
||||
// (defprop) declares instance variables
|
||||
(defprop myField 5)
|
||||
// (prop) declares instance variables
|
||||
(prop myField 5)
|
||||
|
||||
// (defmethod) declares instance methods
|
||||
(defmethod myMethod [] this.myField)
|
||||
// (method) declares instance methods
|
||||
(method myMethod [] this.myField)
|
||||
|
||||
// [...] returns a Kiss array (they have special features and convert implicitly)
|
||||
(defvar myArray [1 2 3])
|
||||
(var myArray [1 2 3])
|
||||
|
||||
// Array access is via nth
|
||||
(defvar myArrayLast (nth myArray -1))
|
||||
(var myArrayLast (nth myArray -1))
|
||||
|
||||
// (collect) turns iterators to arrays
|
||||
(defun _testCollect []
|
||||
(function _testCollect []
|
||||
(Assert.equals "[0,1,2]" (Std.string (collect (range 3)))))
|
||||
|
||||
// Variadic math uses haxe's Lambda.fold under the hood
|
||||
(defvar mySum (+ 1 2 3))
|
||||
(var mySum (+ 1 2 3))
|
||||
|
||||
(defvar myDifference (- 5 4 3))
|
||||
(var myDifference (- 5 4 3))
|
||||
|
||||
(defun _testMultiplication []
|
||||
(function _testMultiplication []
|
||||
(Assert.equals 60 (* 2 5 6))
|
||||
(Assert.equals 5522401584 (* 84 289 89 71 36))
|
||||
(Assert.equals "heyheyhey" (* "hey" 3)))
|
||||
|
||||
// All math operations return floats, none truncate by default
|
||||
(defvar myQuotient (/ 6 3 2 2))
|
||||
(var myQuotient (/ 6 3 2 2))
|
||||
|
||||
(defvar myRemainder (% 10 6))
|
||||
(var myRemainder (% 10 6))
|
||||
|
||||
(defvar myPower (^ 2 8))
|
||||
(var myPower (^ 2 8))
|
||||
|
||||
(defvar &mut myNum 6)
|
||||
(defvar myInc ++myNum)
|
||||
(var &mut myNum 6)
|
||||
(var myInc ++myNum)
|
||||
|
||||
(defvar myMin (min 9 3 7 1))
|
||||
(defvar myMax (max 9 3 7 1))
|
||||
(var myMin (min 9 3 7 1))
|
||||
(var myMax (max 9 3 7 1))
|
||||
|
||||
(defun _testLessThan []
|
||||
(function _testLessThan []
|
||||
(Assert.isTrue (< 1 2 3 4))
|
||||
(Assert.isFalse (< 1 1 3 4))
|
||||
(Assert.isFalse (< 1 12 12)))
|
||||
|
||||
(defun _testLesserEqual []
|
||||
(function _testLesserEqual []
|
||||
(Assert.isTrue (<= 1 2 3 4))
|
||||
(Assert.isTrue (<= 1 1 3 4))
|
||||
(Assert.isFalse (<= 1 12 11)))
|
||||
|
||||
(defun _testGreaterThan []
|
||||
(function _testGreaterThan []
|
||||
(Assert.isTrue (> 4 3 2 1))
|
||||
(Assert.isFalse (> 4 4 2 1))
|
||||
(Assert.isFalse (> 9 3 3)))
|
||||
|
||||
(defun _testGreaterEqual []
|
||||
(function _testGreaterEqual []
|
||||
(Assert.isTrue (>= 4 3 2 1))
|
||||
(Assert.isTrue (>= 4 4 2 1))
|
||||
(Assert.isFalse (>= 9 4 5)))
|
||||
|
||||
(defun _testEqual []
|
||||
(function _testEqual []
|
||||
(Assert.isTrue (= 1 1 1 1))
|
||||
(Assert.isFalse (= 1 2 1 1))
|
||||
(Assert.isTrue (= "hey" "hey" "hey"))
|
||||
@@ -83,7 +83,7 @@
|
||||
(Assert.isFalse (= true false true))
|
||||
(Assert.isTrue (= false false false)))
|
||||
|
||||
(defun _testIf []
|
||||
(function _testIf []
|
||||
(Assert.equals true (if 1 true false))
|
||||
(Assert.equals true (if 0 true false))
|
||||
(Assert.equals true (if -1 true false))
|
||||
@@ -97,28 +97,28 @@
|
||||
(Assert.equals 5 (if true 5))
|
||||
(Assert.equals null (if false 5)))
|
||||
|
||||
(defvar :Int myInt 8)
|
||||
(var :Int myInt 8)
|
||||
|
||||
(defun myTryCatch [:Any e]
|
||||
(function myTryCatch [:Any e]
|
||||
(try
|
||||
(throw e)
|
||||
(catch [:String error] 5)
|
||||
(catch [:Int error] 6)
|
||||
(catch [error] 7)))
|
||||
|
||||
(defun myTypeCheck []
|
||||
(function myTypeCheck []
|
||||
(the Int 5))
|
||||
|
||||
(defun _testConcat []
|
||||
(function _testConcat []
|
||||
(Assert.equals (.toString [1 2 3 4]) (.toString (concat [1] [2 3] [4]))))
|
||||
|
||||
(defun _testGroups []
|
||||
(function _testGroups []
|
||||
(Assert.equals (.toString [[1 2] [3 4]]) (.toString (groups [1 2 3 4] 2)))
|
||||
(Assert.equals (.toString [[1 2 3] [4]]) (.toString (groups [1 2 3 4] 3 Keep)))
|
||||
(try (begin (groups [1 2 3 4] 3 Throw) (Assert.fail))
|
||||
(catch [error] (Assert.pass))))
|
||||
|
||||
(defun _testZip []
|
||||
(function _testZip []
|
||||
(Assert.equals (.toString [[1 2] [3 4]]) (.toString (zipThrow [1 3] [2 4])))
|
||||
(Assert.equals (.toString [[1 2] [3 null]]) (.toString (zipKeep [1 3] [2])))
|
||||
(Assert.equals (.toString [[1 2] [null 4]]) (.toString (zipKeep [1 null] [2 4])))
|
||||
@@ -130,11 +130,11 @@
|
||||
(Assert.equals (.toString [[1 2]]) (.toString (zipDrop [1 2 3 4] [2])))
|
||||
(Assert.equals (.toString [[1 2] [3 4]]) (.toString (apply zipThrow [[1 3] [2 4]]))))
|
||||
|
||||
(defun _testEnumerate []
|
||||
(function _testEnumerate []
|
||||
(Assert.equals (.toString [[0 1] [1 2]]) (.toString (enumerate [1 2])))
|
||||
(Assert.equals (.toString [[1 1] [2 2]]) (.toString (enumerate [1 2] 1))))
|
||||
|
||||
(defun _testLet []
|
||||
(function _testLet []
|
||||
(let [a 5
|
||||
b 6
|
||||
:String c "stuff"]
|
||||
@@ -146,50 +146,50 @@
|
||||
(set a "str2")
|
||||
(Assert.equals "str2" a)))
|
||||
|
||||
(defvar myConstructedString (new String "sup"))
|
||||
(var myConstructedString (new String "sup"))
|
||||
|
||||
(defvar myCond1 (cond
|
||||
(var myCond1 (cond
|
||||
((= 5 6) "not this")
|
||||
((= 8 9) "not this either")
|
||||
((= 1 1) "this one")
|
||||
(true "not the default")))
|
||||
|
||||
(defvar myCond2 (cond
|
||||
(var myCond2 (cond
|
||||
((= 5 6) "not this")
|
||||
((= 8 9) "not this either")
|
||||
((= 2 1) "not the third one")
|
||||
(true "the default")))
|
||||
|
||||
(defvar myCond3 (cond
|
||||
(var myCond3 (cond
|
||||
((= 5 5) "this")
|
||||
(true "default")))
|
||||
|
||||
(defvar myCondFallthrough (cond
|
||||
(var myCondFallthrough (cond
|
||||
(false "not this")))
|
||||
|
||||
(defvar myOr1 (or null 5))
|
||||
(var myOr1 (or null 5))
|
||||
|
||||
(defvar myAnd1 (and 5 6))
|
||||
(defvar myAnd2 (and false 5 6))
|
||||
(defvar myAnd3 (and 5 false 6))
|
||||
(var myAnd1 (and 5 6))
|
||||
(var myAnd2 (and false 5 6))
|
||||
(var myAnd3 (and 5 false 6))
|
||||
|
||||
(defun mySetLocal []
|
||||
(function mySetLocal []
|
||||
(localVar &mut loc "one thing")
|
||||
(set loc "another thing")
|
||||
loc)
|
||||
|
||||
(defvar myNot1 (not 5))
|
||||
(defvar myNot2 !5)
|
||||
(var myNot1 (not 5))
|
||||
(var myNot2 !5)
|
||||
|
||||
(defvar myFilteredList (begin
|
||||
(var myFilteredList (begin
|
||||
(localVar l [-1 -2 5 -3 6])
|
||||
(l.filter (lambda [v] (< 0 v)))))
|
||||
|
||||
(defvar myWhen1 (when true 5 6))
|
||||
(var myWhen1 (when true 5 6))
|
||||
|
||||
(defvar myListOfTen [1 2 3 4 5 6 7 8 9 10])
|
||||
(var myListOfTen [1 2 3 4 5 6 7 8 9 10])
|
||||
|
||||
(defun _testQuickNths []
|
||||
(function _testQuickNths []
|
||||
(Assert.equals 1 (first myListOfTen))
|
||||
(Assert.equals 2 (second myListOfTen))
|
||||
(Assert.equals 3 (third myListOfTen))
|
||||
@@ -202,7 +202,7 @@
|
||||
(Assert.equals 10 (tenth myListOfTen))
|
||||
(Assert.equals 10 (last myListOfTen)))
|
||||
|
||||
(defun _testListDestructuring []
|
||||
(function _testListDestructuring []
|
||||
(localVar [a b c d &mut e f g h i j] myListOfTen)
|
||||
(Assert.equals 1 a)
|
||||
(Assert.equals 2 b)
|
||||
@@ -232,9 +232,9 @@
|
||||
(Assert.equals 10 j)))
|
||||
|
||||
|
||||
(defvar myMetaList [myListOfTen myListOfTen myListOfTen])
|
||||
(var myMetaList [myListOfTen myListOfTen myListOfTen])
|
||||
|
||||
(defun _testDoFor []
|
||||
(function _testDoFor []
|
||||
(localVar &mut c 0)
|
||||
(doFor v myListOfTen
|
||||
(Assert.equals (+ c 1) v)
|
||||
@@ -251,7 +251,7 @@
|
||||
(Assert.equals 9 i)
|
||||
(Assert.equals 10 j)))
|
||||
|
||||
(defun _testFor []
|
||||
(function _testFor []
|
||||
(localVar incrementedList (for v myListOfTen (+ 1 v)))
|
||||
(let [[a b c d e f g h i j] incrementedList]
|
||||
(Assert.equals 2 a)
|
||||
@@ -270,34 +270,34 @@
|
||||
(Assert.equals 5 e)
|
||||
(Assert.equals 10 i)))
|
||||
|
||||
(defun myOptionalFunc [a &opt b c]
|
||||
(function myOptionalFunc [a &opt b c]
|
||||
(Assert.equals 5 a)
|
||||
(Assert.equals null b)
|
||||
(Assert.equals 6 (or c 6))) // (or [optionalVar] [defaultValue]) is the convention for default values
|
||||
|
||||
(defun myRestSum [firstOne &rest :List<Int> others]
|
||||
(function myRestSum [firstOne &rest :List<Int> others]
|
||||
(localVar &mut sum firstOne)
|
||||
(doFor nextOne others (set sum (+ sum nextOne)))
|
||||
sum)
|
||||
|
||||
(defvar myRest1 (myRestSum 5))
|
||||
(defvar myRest2 (myRestSum 1 1 1 1 1))
|
||||
(defvar myRest3 (myRestSum 1 2 2))
|
||||
(var myRest1 (myRestSum 5))
|
||||
(var myRest2 (myRestSum 1 1 1 1 1))
|
||||
(var myRest3 (myRestSum 1 2 2))
|
||||
|
||||
(defun myCombinedOptRest [firstOne &opt secondOne &rest :List<String> thirdAndMore]
|
||||
(function myCombinedOptRest [firstOne &opt secondOne &rest :List<String> thirdAndMore]
|
||||
(localVar &mut concatString (+ firstOne (or secondOne "boop")))
|
||||
(doFor str thirdAndMore (set concatString (+ concatString str)))
|
||||
concatString)
|
||||
|
||||
(defvar myCombined1 (myCombinedOptRest "a" "b" "c" "d"))
|
||||
(defvar myCombined2 (myCombinedOptRest "a"))
|
||||
(defvar myCombined3 (myCombinedOptRest "a" "b"))
|
||||
(var myCombined1 (myCombinedOptRest "a" "b" "c" "d"))
|
||||
(var myCombined2 (myCombinedOptRest "a"))
|
||||
(var myCombined3 (myCombinedOptRest "a" "b"))
|
||||
|
||||
(defun _testFieldExps []
|
||||
(function _testFieldExps []
|
||||
(Assert.equals "hey" (.trim " hey "))
|
||||
(Assert.equals "e" (.charAt (.trim " hey ") 1)))
|
||||
|
||||
(defun _testBreakContinue []
|
||||
(function _testBreakContinue []
|
||||
(let [[a b c]
|
||||
(for val [1 2 3 4 5 6 7 8]
|
||||
(if (> val 6)
|
||||
@@ -309,7 +309,7 @@
|
||||
(Assert.equals 4 b)
|
||||
(Assert.equals 6 c)))
|
||||
|
||||
(defun _testAssert []
|
||||
(function _testAssert []
|
||||
(try
|
||||
(assert false (+ "false " "should " "have " "been " "true"))
|
||||
(catch [:String message]
|
||||
@@ -318,13 +318,13 @@
|
||||
(assert true)
|
||||
(assert ![]))
|
||||
|
||||
(defun _testApply []
|
||||
(function _testApply []
|
||||
(Assert.equals 6 (apply + [1 2 3])))
|
||||
|
||||
(defun applyWithMethod [obj]
|
||||
(function applyWithMethod [obj]
|
||||
(apply .multiply obj [6]))
|
||||
|
||||
(defun _testAnonymousObject []
|
||||
(function _testAnonymousObject []
|
||||
(let [obj
|
||||
(object
|
||||
a "string A"
|
||||
@@ -332,10 +332,10 @@
|
||||
(Assert.equals "string A" obj.a)
|
||||
(Assert.equals 5 obj.b)))
|
||||
|
||||
(defun toOption [:Dynamic value]
|
||||
(function toOption [:Dynamic value]
|
||||
(if value (Some value) None))
|
||||
|
||||
(defun _testCase []
|
||||
(function _testCase []
|
||||
(case (toOption [])
|
||||
(None (Assert.pass))
|
||||
((Some value) (Assert.fail)))
|
||||
@@ -375,7 +375,7 @@
|
||||
(Assert.isTrue (Type.enumEq (Some 5) inner)))
|
||||
(otherwise (Assert.fail))))
|
||||
|
||||
(defun _testMaps []
|
||||
(function _testMaps []
|
||||
(localVar :Map<String,String> myMap [=>"hey" "you"
|
||||
=>"found" "me"])
|
||||
(Assert.equals "you" (dictGet myMap "hey"))
|
||||
@@ -389,7 +389,7 @@
|
||||
(Assert.equals "you" v1)
|
||||
(Assert.equals "me" v2)))
|
||||
|
||||
(defun _testRange []
|
||||
(function _testRange []
|
||||
// With just one arg, it's the max:
|
||||
(localVar &mut :kiss.List<Int> myList (for i (range 5) i))
|
||||
(Assert.equals 4 (nth myList -1))
|
||||
@@ -403,32 +403,32 @@
|
||||
(Assert.equals 9 (second myList))
|
||||
(Assert.equals 15 (last myList)))
|
||||
|
||||
(defun _testRest []
|
||||
(function _testRest []
|
||||
(Assert.equals (.toString [2 3 4]) (.toString (rest [1 2 3 4]))))
|
||||
|
||||
(defun doSomething [:Int->Int func]
|
||||
(function doSomething [:Int->Int func]
|
||||
(func 5))
|
||||
|
||||
(defun itsAMonster [:Null<Map<String,Map<String,Array<String>>>> monsterArg] "but it still compiles")
|
||||
(function itsAMonster [:Null<Map<String,Map<String,Array<String>>>> monsterArg] "but it still compiles")
|
||||
|
||||
(defun _testTypeParsing []
|
||||
(function _testTypeParsing []
|
||||
// Do stuff with functions that take complex type parameters, mostly just to check if it compiles
|
||||
(Assert.equals 5 (doSomething (lambda [i] i)))
|
||||
(Assert.equals 7 (doSomething (lambda [i] (+ i 2))))
|
||||
// Pass null to the really crazy one because I'm lazy:
|
||||
(Assert.equals "but it still compiles" (itsAMonster null)))
|
||||
|
||||
(defmacro defconstfunc [name const] `(defun ,name [] ,const))
|
||||
(defMacro defconstfunc [name const] `(function ,name [] ,const))
|
||||
|
||||
(defconstfunc func5 5)
|
||||
(defconstfunc funcHello "hello")
|
||||
|
||||
(defun _testDefmacro []
|
||||
(function _testDefmacro []
|
||||
(Assert.equals 5 (func5))
|
||||
(Assert.equals "hello" (funcHello)))
|
||||
|
||||
(defvar &mut welcomeCount 0)
|
||||
(defmacro macroWithLogic [name]
|
||||
(var &mut welcomeCount 0)
|
||||
(defMacro macroWithLogic [name]
|
||||
(localVar message1 (ReaderExp.StrExp "Welcome "))
|
||||
(localVar message2 (ReaderExp.StrExp " (Guest #"))
|
||||
(localVar message3 (ReaderExp.StrExp ")"))
|
||||
@@ -436,16 +436,16 @@
|
||||
`(begin (set welcomeCount (+ welcomeCount 1))
|
||||
(+ ,message1 ,name ,message2 (Std.string welcomeCount) ,message3)))
|
||||
|
||||
(defun _testDefmacroWithLogic []
|
||||
(function _testDefmacroWithLogic []
|
||||
(Assert.equals "Welcome Stevo (Guest #1)" (macroWithLogic "Stevo"))
|
||||
(Assert.equals "Welcome Bob (Guest #2)" (macroWithLogic "Bob")))
|
||||
|
||||
// Make sure built-in call aliases don't override user-defined variables
|
||||
(defun _testCallAlias []
|
||||
(function _testCallAlias []
|
||||
(let [map [=>"hey" "you"]]
|
||||
(Assert.equals "you" (dictGet map "hey"))))
|
||||
|
||||
(defun _testAssignArith []
|
||||
(function _testAssignArith []
|
||||
(localVar &mut num 5)
|
||||
(+= num 5 6)
|
||||
(Assert.equals 16 num)
|
||||
@@ -460,7 +460,7 @@
|
||||
(-= num 5 6)
|
||||
(Assert.equals -10 num))
|
||||
|
||||
(defun _testPatternLets []
|
||||
(function _testPatternLets []
|
||||
(let [some5 (Some 5)
|
||||
some6 (Some 6)
|
||||
none None
|
||||
@@ -484,11 +484,11 @@
|
||||
(Assert.fail))
|
||||
(Assert.equals 2 v))))
|
||||
|
||||
(defun _testRawString []
|
||||
(function _testRawString []
|
||||
(Assert.equals #| "\\" |# #"\"#)
|
||||
(Assert.equals #| "\"#" |# ##""#"##))
|
||||
|
||||
(defun _testKissStrings []
|
||||
(function _testKissStrings []
|
||||
(Assert.equals #| "\\\t\r\n\"$" |# "\\\t\r\n\"\$")
|
||||
(let [str "it's"
|
||||
num 3
|
||||
@@ -497,7 +497,7 @@
|
||||
// string interpolation:
|
||||
(Assert.equals "it's 3asy as [a,b,c] [1,2,3]" "$str ${num}asy as $l1 $l2")))
|
||||
|
||||
(defun _testArrowLambdas []
|
||||
(function _testArrowLambdas []
|
||||
(let [withArgs
|
||||
->[arg1 arg2] (+ arg1 arg2)
|
||||
withArg
|
||||
@@ -515,13 +515,13 @@
|
||||
(void)
|
||||
(Assert.equals 6 num)))
|
||||
|
||||
(defvar &mut voidRan false)
|
||||
(defun :Void myVoid [] (set voidRan true))
|
||||
(defun _testVoid []
|
||||
(var &mut voidRan false)
|
||||
(function :Void myVoid [] (set voidRan true))
|
||||
(function _testVoid []
|
||||
(myVoid)
|
||||
(Assert.isTrue voidRan))
|
||||
|
||||
(defun _testLetThrow []
|
||||
(function _testLetThrow []
|
||||
(try
|
||||
{
|
||||
(letThrow
|
||||
@@ -529,4 +529,4 @@
|
||||
(catch [e] (Assert.fail)))
|
||||
(Assert.fail)}
|
||||
(catch [:String e]
|
||||
(Assert.equals "the error we want" e))))
|
||||
(Assert.equals "the error we want" e))))
|
||||
|
@@ -1 +1 @@
|
||||
(defun loadedFunction [] "loaded")
|
||||
(function loadedFunction [] "loaded")
|
||||
|
@@ -1,5 +1,5 @@
|
||||
(defun myFun []
|
||||
(function myFun []
|
||||
(localVar something 5)
|
||||
)
|
||||
|
||||
// This comment used to cause a hard-to-track-down error!
|
||||
// This comment used to cause a hard-to-track-down error!
|
||||
|
@@ -1,4 +1,4 @@
|
||||
(defun myFun []
|
||||
(function myFun []
|
||||
(localVar something 5)
|
||||
// This comment used to cause a hard-to-track-down error!
|
||||
)
|
||||
)
|
||||
|
@@ -1,21 +1,21 @@
|
||||
(defvar runningInHaxe (#if interp true false))
|
||||
(defvar runningInPyOrJs (#if (or py js) true false))
|
||||
(var runningInHaxe (#if interp true false))
|
||||
(var runningInPyOrJs (#if (or py js) true false))
|
||||
|
||||
(defun number []
|
||||
(function number []
|
||||
(let [&mut num 5]
|
||||
(#when interp
|
||||
(+= num 5)
|
||||
(-= num 4))
|
||||
num))
|
||||
|
||||
(defun number2 []
|
||||
(function number2 []
|
||||
(let [&mut num 12]
|
||||
(#unless interp
|
||||
(+= num 5)
|
||||
(-= num 8))
|
||||
num))
|
||||
|
||||
(defvar targetLanguage
|
||||
(var targetLanguage
|
||||
(#cond
|
||||
(cpp "C++")
|
||||
(cs "C#")
|
||||
@@ -24,10 +24,10 @@
|
||||
(js "JavaScript")
|
||||
(python "Python")))
|
||||
|
||||
(defun _testCase []
|
||||
(function _testCase []
|
||||
(#case var1ForCase
|
||||
("var1" (Assert.pass))
|
||||
(otherwise (Assert.fail)))
|
||||
(#case var2ForCase
|
||||
("var2" (Assert.pass))
|
||||
(otherwise (Assert.fail))))
|
||||
(otherwise (Assert.fail))))
|
||||
|
@@ -1,3 +1,3 @@
|
||||
// TODO make a better position reification scheme here
|
||||
(defreadermacro "goop" [stream] #|ReaderExp.CallExp({pos: {file: "bleh", line: 1, column: 1, absoluteChar: 1}, def: ReaderExp.Symbol("Assert.isTrue")}, [{pos: {file: "bleh", line: 1, column: 1, absoluteChar: 1}, def: ReaderExp.Symbol("true")}])|#)
|
||||
(defreadermacro "gloop" [stream] #|ReaderExp.CallExp({pos: {file: "bleh", line: 1, column: 1, absoluteChar: 1}, def: ReaderExp.Symbol("Assert.isFalse")}, [{pos: {file: "bleh", line: 1, column: 1, absoluteChar: 1}, def: ReaderExp.Symbol("false")}])|#)
|
||||
(defReaderMacro "goop" [stream] #|ReaderExp.CallExp({pos: {file: "bleh", line: 1, column: 1, absoluteChar: 1}, def: ReaderExp.Symbol("Assert.isTrue")}, [{pos: {file: "bleh", line: 1, column: 1, absoluteChar: 1}, def: ReaderExp.Symbol("true")}])|#)
|
||||
(defReaderMacro "gloop" [stream] #|ReaderExp.CallExp({pos: {file: "bleh", line: 1, column: 1, absoluteChar: 1}, def: ReaderExp.Symbol("Assert.isFalse")}, [{pos: {file: "bleh", line: 1, column: 1, absoluteChar: 1}, def: ReaderExp.Symbol("false")}])|#)
|
@@ -1,4 +1,4 @@
|
||||
(defun _testListEating []
|
||||
(function _testListEating []
|
||||
// TODO document that list-eating only works on explictly Array-typed variables
|
||||
(let [:Array<Int> l [1 2 3 4]]
|
||||
(case l
|
||||
@@ -29,4 +29,4 @@
|
||||
(Assert.equals (.toString [1 2 3]) (.toString rest))
|
||||
(Assert.equals 4 last))
|
||||
(otherwise
|
||||
(Assert.fail)))))
|
||||
(Assert.fail)))))
|
||||
|
@@ -1,22 +1,22 @@
|
||||
(defmacro defMultiple [varName funcName]
|
||||
(defMacro defMultiple [varName funcName]
|
||||
`{
|
||||
(defvar ,varName 5)
|
||||
(defun ,funcName [] 6)})
|
||||
(var ,varName 5)
|
||||
(function ,funcName [] 6)})
|
||||
|
||||
(defMultiple myVar myFunc)
|
||||
|
||||
(defmacro variadicPlus [&rest l]
|
||||
(defMacro variadicPlus [&rest l]
|
||||
`(+ ,@l))
|
||||
(defmacro listPlus [l]
|
||||
(defMacro listPlus [l]
|
||||
`(+ ,@l))
|
||||
|
||||
// Both forms of passing expression lists to macros should work:
|
||||
(defun sum1 [] (variadicPlus 1 2 3))
|
||||
(defun sum2 [] (listPlus [1 2 3]))
|
||||
(function sum1 [] (variadicPlus 1 2 3))
|
||||
(function sum2 [] (listPlus [1 2 3]))
|
||||
|
||||
// You should be able to run list comprehensions on expressions
|
||||
// and put the pieces back together in a modular way
|
||||
(defmacro altDefun [name args &body body]
|
||||
(defMacro altDefun [name args &body body]
|
||||
(let [argPairs
|
||||
(groups (expList args) 2)
|
||||
untypedArgs
|
||||
@@ -30,22 +30,22 @@
|
||||
(print name)
|
||||
(letBindings.push `(the ,type ,name)))
|
||||
(print letBindings)
|
||||
`(defun ,name ,untypedArgs
|
||||
`(function ,name ,untypedArgs
|
||||
(let ,letBindings ,@body))))
|
||||
|
||||
(altDefun nameAndNumber [name String number Int]
|
||||
"$name $number")
|
||||
|
||||
// If for whatever reason, you wanted to make a variable called print
|
||||
(undefalias &call print)
|
||||
(defvar print 9)
|
||||
(undefAlias &call print)
|
||||
(var print 9)
|
||||
|
||||
(defalias &ident alias 5)
|
||||
(undefalias &ident alias)
|
||||
(defvar alias 9)
|
||||
(defun aliasValue [] alias)
|
||||
(defAlias &ident alias 5)
|
||||
(undefAlias &ident alias)
|
||||
(var alias 9)
|
||||
(function aliasValue [] alias)
|
||||
|
||||
// If for whatever reason, you wanted to make a function called and
|
||||
(undefmacro and)
|
||||
(defun and [a b] (+ a b))
|
||||
(defun andValue [] (and 5 6))
|
||||
(undefMacro and)
|
||||
(function and [a b] (+ a b))
|
||||
(function andValue [] (and 5 6))
|
||||
|
@@ -1,8 +1,8 @@
|
||||
(defvar &mut staticCount 0)
|
||||
(defvar &mut instanceCount 0)
|
||||
(var &mut staticCount 0)
|
||||
(var &mut instanceCount 0)
|
||||
|
||||
(defmethod new []
|
||||
(method new []
|
||||
(once
|
||||
(+= staticCount 1))
|
||||
(oncePerInstance
|
||||
(+= instanceCount 1)))
|
||||
(+= instanceCount 1)))
|
||||
|
@@ -1,31 +1,31 @@
|
||||
(defreadermacro &start "!" [stream]
|
||||
(defReaderMacro &start "!" [stream]
|
||||
(let [line (stream.expect "a string line" (lambda [] (stream.takeLine)))]
|
||||
(ReaderExp.StrExp line)))
|
||||
|
||||
(defun myLine []
|
||||
(function myLine []
|
||||
!String that takes the rest of the line
|
||||
)
|
||||
|
||||
(defun myBool []
|
||||
(function myBool []
|
||||
(begin !false))
|
||||
|
||||
(defalias &call pluppers +)
|
||||
(defalias &ident fluffers 5)
|
||||
(defalias &ident buffers 4)
|
||||
(defAlias &call pluppers +)
|
||||
(defAlias &ident fluffers 5)
|
||||
(defAlias &ident buffers 4)
|
||||
|
||||
(defvar mySum (pluppers fluffers buffers))
|
||||
(var mySum (pluppers fluffers buffers))
|
||||
|
||||
// Read b c directly as strings
|
||||
(defreadermacro ["b" "c"] [stream] #|ReaderExp.StrExp(stream.expect("b, or c", function () stream.takeChars(1)))|#)
|
||||
(defReaderMacro ["b" "c"] [stream] #|ReaderExp.StrExp(stream.expect("b, or c", function () stream.takeChars(1)))|#)
|
||||
|
||||
(defvar str1 b)
|
||||
(defvar str2 c)
|
||||
(var str1 b)
|
||||
(var str2 c)
|
||||
|
||||
// rassert asserts the next expression without parens
|
||||
(defreadermacro "rassert" [stream] `(assert ,(read stream)))
|
||||
(defReaderMacro "rassert" [stream] `(assert ,(read stream)))
|
||||
|
||||
(defun _testQuasiquoteMacro []
|
||||
(function _testQuasiquoteMacro []
|
||||
rassert [5]
|
||||
rassert b
|
||||
rassert fluffers
|
||||
(Assert.pass))
|
||||
(Assert.pass))
|
||||
|
Reference in New Issue
Block a user