diff --git a/README.md b/README.md index e1dcf22..9fab8e8 100644 --- a/README.md +++ b/README.md @@ -1,2 +1,81 @@ # PebbLisp -A very basic LISP implementation with an interpreter and editor written for the Pebble +A very basic LISP implementation with an interpreter and editor written for the Pebble. + +# Writing in PebbLisp +PebbLisp includes several built-ins functionalities. + +## Def +`def` stores a given object into the environment with the given symbol. The general form is: + +`(def symbol object)` + +As an example, to store a long greeting message into the short symbol `g`: + +`(def g "Hello, how are you today?")` + +`g` will then evaluate to `"Hello, how are you today"`. + +> Remember that defining an object with the same symbol as an object that already exists is possible, but deletes the original object from the environment! + +## If +`if` checks a given condition. If the condition evaluates to true, the first given expression is returned. If false, the second expression is returned. The general format is: + +`(if condition expr1 expr2)` + +The condition will typically be involve a comparison operator. For example: + +`(if (< 5 10) "Yee" "haw")` + +Would return `"Yee"`, as `(< 5 10)` aka `5 < 10` evaluates to true. + +## Fn +`fn` creates a lambda with a (theoretically) arbitrary number of arguments to be evaluated on call. The general form is: + +`(fn (arg-list) (lambda-body))` + +A lambda will commonly be stored under a `def` symbol, for example: + +`(def sq (fn (a) (* a a)))` + +Defines a simple lambda to square a given number. Calling it is as simple as `(sq 5)`, which returns `25`. + +Lambdas can also be applied anonymously, as in `((fn (a) (* a a)) 5)`, which also returns `25`, but this is most useful when using something like `map`. For example: + +`(map (fn (a) (* a a)) (1 2 3 5 8 13 21 34))` + +Uses an anonymous lambda to square each element in the list. This is particularly useful on a low-memory device like the Pebble, where it may be useful to avoid storing the named lambda object in the environment. + +## Cat +`cat` returns its arguments concatenated as strings. It has the same general form as arithmetic operators + +`(cat expr1 expr2 ...)` + +For example, combining numbers and strings: + +`(cat "There are " 5 " cats")` + +Would return `There are 5 cats`. + +A `cat` operation is applied implicitly when using `+` with strings, but this may result in confusing behavior when combined with number objects, due to the left-associativity of operators. For example, `(+ 5 10 " cats")` results in `15 cats` but `(+ "Cats: " 5 10)` results in `Cats: 510`. + +## Map +`map` applies a given lambda to each element in a given list and returns a list composed of each result. The general form of a `map` expression is + +`(map lambda (input-list))` + +For example, using a `sq` lambda: + +`(map sq (1 2 3 4 5 6 7 8 9 10)` + +Would return `( 1 4 9 16 25 36 49 64 81 100 )`, with each element being the square of the corresponding element in the input list. + +## Fil +`fil` returns a filtered list, based on a given list and a given condition. Partial function support in PebbLisp is nowhere near comprehensive, but `fil` operates on the bare notion that currently exists. The general form of a `fil` expression is + +`(fil (partial-condition) (candidate-list))` + +Each element in the candidate list is compared against the partial condition. If the comparison returns true, it is added to the returned list. For example + +`(fil (< 100) (20 150 30 200))` + +would return `( 150 200 )`, as no other elements fit the condition `(< 100 n)`. \ No newline at end of file