# Ginger A lisp-like language built on the go programming language. The ideas are still a work-in-progress, and this repo is where I'm jotting down my notes. # Goals I have some immediate goals I'm trying to achieve with this syntax: * Everything is strings (except numbers, functions, and data structures). There is no symbol type, atom type, keyword type, etc... they're all just strings. * There is no `defmacro`. Macro creation and usage is simply an inherent feature of the language syntax. # Walkthrough This is a number which evalutates to 5: ``` 5 ``` This is a string, as it contains no whitespace: ``` ImJustAString ``` This is also a string, it can contain anything: ``` "! I'm the king of the world !" ``` This is a list. It evaluates to a linked-list of four strings: ``` (a b c d) ``` This is a vector of those same elements. It's like a list, but has some slightly different properties. We'll mostly be using lists: ``` [a b c d] ``` This is a string ``` + ``` `:` is the evaluator. This evaluates to a function which adds its arguments: ``` :+ ``` This evaluates to list whose elements are a function and two numbers: ``` (:+ 1 2) ``` This evaluates to the number 5: ``` :(:+ 1 2) ``` The `fn` function can be used to define a new function. This evaluates to an anonymous function which adds one to its argument and returns it: ``` :(:fn [x] :(:+ :x 1)) ``` The `def` function can be used to bind some value to a new variable: ``` :(:def foo bar) # Now :foo will evaluate to the string bar :(:def incr (:fn [x] :(:+ :x 1))) # Now :incr will evaulate to a function which adds 1 to its argument #defn is a shortcut for the above :(:defn incr [x] :(:+ :x 1)) ``` There are also maps. A map's keys can be any value(?). A map's values can be any value. This evaluates to a map with 2 key/val pairs: ``` { foo :foo bar (:incr 4) } ``` `.` is the half-evaluator. It only works on lists, and runs the function given in the first argument with the unevaluated arguments (even if they have `:` in front). You can generate new code to run on the fly (macros) using the normal `fn`. This evaluates to a `let`-like function, except it forces you to use the capitalized variable names in the body (utterly useless): ``` :(:defn caplet [mapping body...] # elem-map maps over every element in a list, embedded or otherwise ::(:elem-map :(:fn [x] :(:if (mapping :(:slice :x 1)) (capitalize :x) :x)) :body)) #Usage .(:caplet [foo "this is foo" dog "this is dog"] :(:println :Foo) :(:println :Dog)) ```