Difference between revisions of "Calico Scheme"

From IPRE Wiki
Jump to: navigation, search
(quote, quasiquote, and unquote)
Line 2: Line 2:
  
 
Calico Scheme is a new implementation of a Scheme-based language for Calico. It implements many core Scheme functions, but also adds some functionality to bring it into line with the other modern languages like Python and Ruby. In can run inside Calico as a DLL, or can run in Python.
 
Calico Scheme is a new implementation of a Scheme-based language for Calico. It implements many core Scheme functions, but also adds some functionality to bring it into line with the other modern languages like Python and Ruby. In can run inside Calico as a DLL, or can run in Python.
 +
 +
This page describes Calico Scheme version 3.0.0.
 +
 +
The Scheme in Python program can be found here:
 +
 +
https://bitbucket.org/ipre/calico/raw/master/languages/Scheme/Scheme/calicoscheme.py
 +
 +
The Scheme in C# can be found in Calico, installed from here:
 +
 +
[[Calico Download]]
  
 
= Scheme Extensions =
 
= Scheme Extensions =
Line 12: Line 22:
 
= Commands =
 
= Commands =
  
=== quote, quasiquote, and unquote ===
+
The following are the functions, syntax, and special forms for Calico Scheme.
 
+
<pre>
+
(quote item)
+
'item
+
</pre>
+
 
+
A quoted item (represented by a single-quote) is a symbol (if item is an atom), or is a list of quoted items if item is a list. Literals that are quoted are just the literals.
+
 
+
Examples:
+
 
+
<pre>
+
'symbol => symbol
+
'(a list of items) => (a list of items)
+
</pre>
+
 
+
<pre>
+
(quasiquote item)
+
`item
+
</pre>
+
 
+
Quasiquote (represented by a back-quote) is like a regular quoted item; however, with a quasiquote, unquoted (represented with a comma) items are evaluated.
+
 
+
Examples:
+
 
+
<pre>
+
(quasiquote (list (unquote (+ 1 2)) 4)) => (list 3 4)
+
`(list ,(+ 1 2) 4) => (list 3 4)
+
</pre>
+
 
+
Notice that the (+ 1 2) is evaluated.
+
  
 
=== % ===
 
=== % ===
Line 62: Line 42:
 
Multiply will take a number of arguments and give you the total of all numbers multiplied with each other.
 
Multiply will take a number of arguments and give you the total of all numbers multiplied with each other.
  
Example:
+
Examples:
  
 
<pre>
 
<pre>
 
(*) => 1
 
(*) => 1
 +
 
(* 12) => 12
 
(* 12) => 12
 +
 
(* 2 3) => 6
 
(* 2 3) => 6
 +
 
(* 2 3 4) => 24
 
(* 2 3 4) => 24
 
</pre>
 
</pre>
Line 101: Line 84:
 
Divide will divide one number from the previous.
 
Divide will divide one number from the previous.
  
Example:
+
Examples:
  
 
<pre>
 
<pre>
 
(/) => 1
 
(/) => 1
 +
 
(/ 2) => 1/2
 
(/ 2) => 1/2
 +
 
(/ 3 4) => 3/4
 
(/ 3 4) => 3/4
 
</pre>
 
</pre>
Line 185: Line 170:
 
(and ...)
 
(and ...)
  
And will return #f as soon as it encounters a #f in the items. If no #f is encountered, it returns the last item.
+
And will return #f as soon as it encounters a #f in the items (eg, it short circuits without further evaluation of arguments). If no #f is encountered, it returns the last item.
  
Example:
+
Examples:
  
 
<pre>
 
<pre>
 
(and 4 1 2 #t (quote ()) 0) => 0
 
(and 4 1 2 #t (quote ()) 0) => 0
 +
 
(and 4 1 2 #t '() 3) => 3
 
(and 4 1 2 #t '() 3) => 3
 +
 
(and 4 1 2 #f '() 0) => #f
 
(and 4 1 2 #f '() 0) => #f
 
</pre>
 
</pre>
Line 205: Line 192:
 
<pre>
 
<pre>
 
(append (quote (1 2 3)) (quote (4 5 6))) => (1 2 3 4 5 6)
 
(append (quote (1 2 3)) (quote (4 5 6))) => (1 2 3 4 5 6)
 +
 
(append '(1 2 3) '(4 5 6)) => (1 2 3 4 5 6)
 
(append '(1 2 3) '(4 5 6)) => (1 2 3 4 5 6)
 +
 
(append '(1 2 3) '(4 5 6) '(7 8 9)) => (1 2 3 4 5 6 7 8 9)
 
(append '(1 2 3) '(4 5 6) '(7 8 9)) => (1 2 3 4 5 6 7 8 9)
 +
 
(append '(1 2 3) '(4 5 6) 7) => (1 2 3 4 5 6 . 7)
 
(append '(1 2 3) '(4 5 6) 7) => (1 2 3 4 5 6 . 7)
 
</pre>
 
</pre>
Line 212: Line 202:
 
=== apply ===
 
=== apply ===
  
(apply ...)
+
(apply f args)
  
Example:
+
Apply takes a function and applies it to a list of arguments. (apply f '(1 2)) operates as if it were written (f 1 2).
 +
 
 +
Examples:
  
 
<pre>
 
<pre>
 
(apply car (quote ((1)))) => 1
 
(apply car (quote ((1)))) => 1
 +
 
(apply car '((1))) => 1
 
(apply car '((1))) => 1
 
</pre>
 
</pre>
Line 225: Line 218:
 
(assq ...)
 
(assq ...)
  
Example:
+
Find an association using the eq? operator. Given an item, look it up in a list of pair of associations.
 +
 
 +
Examples:
  
 
<pre>
 
<pre>
 
(assq 1 (quote ((1 2) (3 4)))) => (1 2)
 
(assq 1 (quote ((1 2) (3 4)))) => (1 2)
 +
 
(assq 1 '((1 2) (3 4))) => (1 2)
 
(assq 1 '((1 2) (3 4))) => (1 2)
 
</pre>
 
</pre>
Line 236: Line 232:
 
(assv ...)
 
(assv ...)
  
Example:
+
Find an association using the eqv? operator. Given an item, look it up in a list of pair of associations.
 +
 
 +
Examples:
  
 
<pre>
 
<pre>
 
(assv 1 (quote ((1 2) (3 4)))) => (1 2)
 
(assv 1 (quote ((1 2) (3 4)))) => (1 2)
 +
 
(assv 1 '((1 2) (3 4))) => (1 2)
 
(assv 1 '((1 2) (3 4))) => (1 2)
 
</pre>
 
</pre>
Line 245: Line 244:
 
=== atom? ===
 
=== atom? ===
  
(atom? ...)
+
(atom? item)
 +
 
 +
Returns #t if item is an atom.  
  
 
Example:
 
Example:
Line 255: Line 256:
 
=== boolean? ===
 
=== boolean? ===
  
(boolean? ...)
+
(boolean? item)
  
Example:
+
Returns #t if item is a boolean (#t or #f) and #f otherwise.
 +
 
 +
Examples:
  
 
<pre>
 
<pre>
 
(boolean? #t) => #t
 
(boolean? #t) => #t
 +
 +
(boolean? #f) => #t
 
</pre>
 
</pre>
  
 
=== car, cdr and related ===
 
=== car, cdr and related ===
  
(caaaar ...)
+
Given one of these functions and a list, it will return part of the list.
  
Example:
+
(car ...)
 +
 
 +
Examples:
 +
 
 +
<pre>
 +
(car '(a b)) => a
 +
 
 +
(car '(a . b)) => a
 +
 
 +
(car '((a) b) => (a)
 +
 
 +
(car (quote (((((hello there) this is a test) what is this) another item) in the list)))
 +
    => ((((hello there) this is a test) what is this) another item)
 +
</pre>
 +
 
 +
(cdr ...)
 +
 
 +
Returns everything in a list, except the car.
 +
 
 +
Examples:
 +
 
 +
<pre>
 +
(cdr '(a b)) => (b)
 +
 
 +
(cdr '(a . b) => b
 +
 
 +
(cdr (quote (((((hello there) this is a test) what is this) another item) 1 2 3))) => (1 2 3)
 +
</pre>
 +
 
 +
(caaaar list)
 +
 
 +
Is the same as (car (car (car (car list)))).
 +
 
 +
Examples:
  
 
<pre>
 
<pre>
 
(caaaar (quote (((((hello there) this is a test) what is this) another item) in the list))) => (hello there)
 
(caaaar (quote (((((hello there) this is a test) what is this) another item) in the list))) => (hello there)
 +
 
(caaaar '(((((hello there) this is a test) what is this) another item) in the list)) => (hello there)
 
(caaaar '(((((hello there) this is a test) what is this) another item) in the list)) => (hello there)
 
</pre>
 
</pre>
Line 376: Line 415:
 
<pre>
 
<pre>
 
(cadr (quote (((((hello there) this is a test) what is this) another item) in the list))) => in
 
(cadr (quote (((((hello there) this is a test) what is this) another item) in the list))) => in
</pre>
 
 
(car ...)
 
 
Example:
 
 
<pre>
 
(car (quote (((((hello there) this is a test) what is this) another item) in the list))) => ((((hello there) this is a test) what is this) another item)
 
 
</pre>
 
</pre>
  
Line 496: Line 527:
 
<pre>
 
<pre>
 
(cddr (quote (((((hello there) this is a test) what is this) another item) 1 2 3))) => (2 3)
 
(cddr (quote (((((hello there) this is a test) what is this) another item) 1 2 3))) => (2 3)
</pre>
 
 
(cdr ...)
 
 
Example:
 
 
<pre>
 
(cdr (quote (((((hello there) this is a test) what is this) another item) 1 2 3))) => (1 2 3)
 
 
</pre>
 
</pre>
  
Line 510: Line 533:
 
(case ...)
 
(case ...)
  
Example:
+
For use in handling different cases. Returns the first expression that matches. "else" acts as it were #t (always matches).
 +
 
 +
Examples:
  
 
<pre>
 
<pre>
(case (quote thing1) (thing2 1) (thing1 2)) => 2
+
(case 'thing1  
(case (quote thing1) (thing2 1) ((thing1 thing3) 2)) => 2
+
  (thing2 1)  
(case (quote thingx) (thing2 1) ((thing1 thing3) 2) (else 3)) => 3
+
  (thing1 2))           => 2
 +
 
 +
(case 'thing1  
 +
  (thing2 1)  
 +
  ((thing1 thing3) 2)) => 2
 +
 
 +
(case 'thingx  
 +
  (thing2 1)  
 +
  ((thing1 thing3) 2)  
 +
  (else 3))             => 3
 
</pre>
 
</pre>
  
=== cd ===
+
=== cd/current-directory ===
  
 +
<pre>
 
(cd ...)
 
(cd ...)
 +
(current-directory)
 +
</pre>
 +
 +
Change/current directory. Given a string, will change to that directory. If you leave out the argument, it returns the current directory.
  
 
Example:
 
Example:
  
 
<pre>
 
<pre>
(cd) => ""
+
(cd)                   => ""
 +
(cd "..")              => moves up one directory
 
</pre>
 
</pre>
  
Line 531: Line 571:
  
 
(char->integer ...)
 
(char->integer ...)
 +
 +
Converts a character into an integer.
  
 
Example:
 
Example:
Line 541: Line 583:
  
 
(char->string ...)
 
(char->string ...)
 +
 +
Converts a character into a string.
  
 
Example:
 
Example:
Line 550: Line 594:
 
=== char-alphabetic? ===
 
=== char-alphabetic? ===
  
(char-alphabetic? ...)
+
(char-alphabetic? c)
  
Example:
+
Is c an alphabetic character?
 +
 
 +
Examples:
  
 
<pre>
 
<pre>
 
(char-alphabetic? #\A) => #t
 
(char-alphabetic? #\A) => #t
 +
 +
(char-alphabetic? #\1) => #f
 
</pre>
 
</pre>
  
 
=== char-numeric? ===
 
=== char-numeric? ===
  
(char-numeric? ...)
+
(char-numeric? c)
 +
 
 +
Is c an numeric character?
  
 
Example:
 
Example:
Line 571: Line 621:
  
 
(char-whitespace? ...)
 
(char-whitespace? ...)
 +
 +
Is c a whitespace (e.g. tab, space, newline) character?
  
 
Example:
 
Example:
Line 576: Line 628:
 
<pre>
 
<pre>
 
(char-whitespace? #\t) => #f
 
(char-whitespace? #\t) => #f
</pre>
 
  
=== char-whitespace? ===
+
(char-whitespace? #\tab) => #t
  
(char-whitespace? ...)
+
(char-whitespace? #\newline) => #t
  
Example:
 
 
<pre>
 
(char-whitespace? #\ ) => #t
 
</pre>
 
 
=== char-whitespace? ===
 
 
(char-whitespace? ...)
 
 
Example:
 
 
<pre>
 
(char-whitespace? #\
 
) => #t
 
</pre>
 
 
=== char-whitespace? ===
 
 
(char-whitespace? ...)
 
 
Example:
 
 
<pre>
 
 
(char-whitespace? #\a) => #f
 
(char-whitespace? #\a) => #f
 
</pre>
 
</pre>
Line 612: Line 639:
  
 
(char=? ...)
 
(char=? ...)
 +
 +
Returns #t if two characters are the same.
  
 
Example:
 
Example:
Line 617: Line 646:
 
<pre>
 
<pre>
 
(char=? #\a #\a) => #t
 
(char=? #\a #\a) => #t
</pre>
 
  
=== char=? ===
 
 
(char=? ...)
 
 
Example:
 
 
<pre>
 
 
(char=? #\a #\b) => #f
 
(char=? #\a #\b) => #f
 
</pre>
 
</pre>
Line 631: Line 652:
 
=== char? ===
 
=== char? ===
  
(char? ...)
+
(char? item)
 +
 
 +
Is item a character?
  
 
Example:
 
Example:
Line 642: Line 665:
  
 
(cond ...)
 
(cond ...)
 +
 +
Asks a series of questions, and if true, returns the associated expression. "else" acts as if it were "#t".
  
 
Example:
 
Example:
  
 
<pre>
 
<pre>
(cond (#f 1) (else 2)) => 2
+
(cond  
 +
  (#f 1)  
 +
  (else 2))       => 2
 
</pre>
 
</pre>
  
 
=== cons ===
 
=== cons ===
  
(cons ...)
+
(cons item1 item2)
  
Example:
+
Constructs a new cons cell by cons-ing item1 onto item2. A proper list ends in the special symbol, '() pronounced "empty list".
 +
An improper list ends with a dot, followed by the last item.
 +
 
 +
Examples:
  
 
<pre>
 
<pre>
(cons 1 (quote ())) => (1)
+
(cons 1 '())     => (1)
</pre>
+
  
=== current-directory ===
+
(cons 1 2)       => (1 . 2)
 
+
(current-directory ...)
+
 
+
Example:
+
 
+
<pre>
+
(current-directory) => "."
+
 
</pre>
 
</pre>
  
 
=== current-environment ===
 
=== current-environment ===
  
(current-environment ...)
+
(current-environment)
 +
 
 +
Get the current environment.
  
 
Example:
 
Example:
  
 
<pre>
 
<pre>
(length (dir (current-environment))) => 160
+
(current-environment)                 => the current environment
 
</pre>
 
</pre>
  
 
=== current-time ===
 
=== current-time ===
  
(current-time ...)
+
(current-time)
 +
 
 +
Returns the current time.
  
 
Example:
 
Example:
Line 704: Line 730:
  
 
(dict ...)
 
(dict ...)
 +
 +
Make a dictionary.
  
 
Example:
 
Example:
Line 715: Line 743:
 
(dir ...)
 
(dir ...)
  
Object properties and enviroment variables.
+
Object properties and environment variables.
  
 
  ==> (dir)
 
  ==> (dir)
Line 748: Line 776:
  
 
(eq? ...)
 
(eq? ...)
 +
 +
Tests if two object are the same.
  
 
Example:
 
Example:
Line 758: Line 788:
  
 
(equal? ...)
 
(equal? ...)
 +
 +
Tests if two things evaluate to the same value.
  
 
Example:
 
Example:
Line 768: Line 800:
  
 
(eqv? ...)
 
(eqv? ...)
 +
 +
Slightly less strict that eq?.
  
 
Example:
 
Example:
Line 777: Line 811:
 
=== error ===
 
=== error ===
  
(error ...)
+
(error name message)
 +
 
 +
Throw an exception. See also the try/catch examples below.
  
 
Example:
 
Example:
Line 787: Line 823:
 
=== eval ===
 
=== eval ===
  
(eval ...)
+
(eval item)
 +
 
 +
Evaluate an expression.
  
 
Example:
 
Example:
  
 
<pre>
 
<pre>
(eval (quote (+ 1 2))) => 3
+
(eval '(+ 1 2)) => 3
 
</pre>
 
</pre>
  
Line 798: Line 836:
  
 
(eval-ast ...)
 
(eval-ast ...)
 +
 +
Evaluate an abstract syntax tree.
  
 
Example:
 
Example:
Line 807: Line 847:
 
=== even? ===
 
=== even? ===
  
(even? ...)
+
(even? number)
 +
 
 +
Returns #t if a number is even.
  
 
Example:
 
Example:
Line 817: Line 859:
 
=== float ===
 
=== float ===
  
(float ...)
+
(float number)
 +
 
 +
Returns a floating point version of a number.
  
 
Example:
 
Example:
Line 827: Line 871:
 
=== for-each ===
 
=== for-each ===
  
(for-each ...)
+
(for-each f sequence)
 +
 
 +
Maps a function f onto a sequence, but doesn't return anything. Sequence can be a string, list, vector, or other iterator. for-each is used for its side-effects.
  
 
Example:
 
Example:
Line 837: Line 883:
 
=== format ===
 
=== format ===
  
(format ...)
+
(format message arg ...)
 +
 
 +
Formats a message using the following special codes:
 +
 
 +
* ~a - "any", prints as display does
 +
* ~s - "s-expression", prints as write does
 +
* ~% - newline
  
 
Example:
 
Example:
  
 
<pre>
 
<pre>
(format "~a ~s ~%" "hello" "hello") => "hello \"hello\"
+
(format "~a ~s ~%" "hello1" "hello2") outputs: hello1 \"hello2\"  
"
+
 
</pre>
 
</pre>
  
 
=== get-stack-trace ===
 
=== get-stack-trace ===
  
(get-stack-trace ...)
+
(get-stack-trace)
 +
 
 +
Gets the current stack trace. You can disable stack traces with (use-stack-trace #f).
  
 
Example:
 
Example:
Line 860: Line 913:
 
Modules provide an easy method for structuring hierarchies of libraries and code.
 
Modules provide an easy method for structuring hierarchies of libraries and code.
  
'''Import'''
+
====import====
  
 
  (import <string-exp>)
 
  (import <string-exp>)
Line 877: Line 930:
 
'''import''' uses the local environment, while '''load''' uses the toplevel-environment.
 
'''import''' uses the local environment, while '''load''' uses the toplevel-environment.
  
'''Lookup'''
+
====Lookup====
  
 
  module.name
 
  module.name
Line 888: Line 941:
 
=== int ===
 
=== int ===
  
(int ...)
+
(int number)
 +
 
 +
Returns an integer form of the number. Note that this rounds to the nearest integer.
  
 
Example:
 
Example:
Line 899: Line 954:
  
 
(integer->char ...)
 
(integer->char ...)
 +
 +
Converts an integer to a character.
  
 
Example:
 
Example:
Line 908: Line 965:
 
=== iter? ===
 
=== iter? ===
  
(iter? ...)
+
(iter? item)
 +
 
 +
Returns #t if item is an iterator.
  
 
Example:
 
Example:
Line 918: Line 977:
 
=== length ===
 
=== length ===
  
(length ...)
+
(length ls)
 +
 
 +
Returns the length of a list, ls. Note that this does not recurse into the list, but only counts the toplevel items, even if those are lists.
  
 
Example:
 
Example:
Line 929: Line 990:
  
 
(let ...)
 
(let ...)
 +
 +
One method of creating local variables.
  
 
Example:
 
Example:
Line 939: Line 1,002:
  
 
(let* ...)
 
(let* ...)
 +
 +
Allows the creation of variables whose value depends on previous variables.
  
 
Example:
 
Example:
Line 945: Line 1,010:
 
(let* ((x 1) (y (+ x 1))) y) => 2
 
(let* ((x 1) (y (+ x 1))) y) => 2
 
</pre>
 
</pre>
 +
 +
In this example, note that y depends on x.
  
 
=== letrec ===
 
=== letrec ===
  
 
(letrec ...)
 
(letrec ...)
 +
 +
Allows creating recursively defined values.
  
 
Example:
 
Example:
  
 
<pre>
 
<pre>
(letrec ((loop (lambda (n) (if (= n 0) (quote ok) (loop (- n 1)))))) (loop 10)) => ok
+
(letrec ((loop (lambda (n)  
 +
                  (if (= n 0)  
 +
                      (quote ok)  
 +
                      (loop (- n 1))))))  
 +
    (loop 10))                             => ok
 
</pre>
 
</pre>
  
Line 959: Line 1,032:
  
 
(list ...)
 
(list ...)
 +
 +
Create a new list by consing the items onto each other, ending in '(), creating a proper list.
  
 
Example:
 
Example:
Line 969: Line 1,044:
  
 
(list->string ...)
 
(list->string ...)
 +
 +
Converts a list of characters into a string.
  
 
Example:
 
Example:
Line 979: Line 1,056:
  
 
(list->vector ...)
 
(list->vector ...)
 +
 +
Converts a list into a vector. A vector has a fixed length, and can index directly into a position.
  
 
Example:
 
Example:
Line 985: Line 1,064:
 
(list->vector (quote (1 2 3))) => [1, 2, 3]
 
(list->vector (quote (1 2 3))) => [1, 2, 3]
 
</pre>
 
</pre>
 +
 +
In Python, Scheme uses the Python List as a vector. In C#, Scheme uses an array to represent a vector.
  
 
=== list-ref ===
 
=== list-ref ===
  
 
(list-ref ...)
 
(list-ref ...)
 +
 +
A convenient method to get an item from a list. This is no more efficient than a series of car/cdrs.
  
 
Example:
 
Example:
Line 999: Line 1,082:
  
 
(list? ...)
 
(list? ...)
 +
 +
Returns #t if an item is a proper list, or the empty list '().
  
 
Example:
 
Example:
Line 1,009: Line 1,094:
  
 
(make-set ...)
 
(make-set ...)
 +
 +
Creates a list of unique items.
  
 
Example:
 
Example:
Line 1,018: Line 1,105:
 
=== make-vector ===
 
=== make-vector ===
  
(make-vector ...)
+
(make-vector size)
 +
 
 +
Creates a vector of a specific size.
  
 
Example:
 
Example:
Line 1,028: Line 1,117:
 
=== map ===
 
=== map ===
  
(map ...)
+
(map f sequence)
 +
 
 +
Applies a function to all elements in a sequence, and returns the resulting values in a list.
  
 
Example:
 
Example:
Line 1,038: Line 1,129:
 
=== member ===
 
=== member ===
  
(member ...)
+
(member item ls)
 +
 
 +
Check to see if item is in a list. If it is in the list, return the rest of the list. If not, return #f.
  
 
Example:
 
Example:
Line 1,048: Line 1,141:
 
=== memq ===
 
=== memq ===
  
(memq ...)
+
(memq item ls)
 +
 
 +
Check if item is in ls (like member) but using the eq? operator.
  
 
Example:
 
Example:
Line 1,059: Line 1,154:
  
 
(memv ...)
 
(memv ...)
 +
 +
Check if item is in ls (like member) but using the eqv? operator.
  
 
Example:
 
Example:
Line 1,068: Line 1,165:
 
=== not ===
 
=== not ===
  
(not ...)
+
(not item)
 +
 
 +
Flips the boolean value of item.
  
 
Example:
 
Example:
Line 1,078: Line 1,177:
 
=== null? ===
 
=== null? ===
  
(null? ...)
+
(null? item)
 +
 
 +
Checks to see if an item is eq? to the empty list, '().
  
 
Example:
 
Example:
Line 1,089: Line 1,190:
  
 
(number->string ...)
 
(number->string ...)
 +
 +
Convert a number into a string.
  
 
Example:
 
Example:
Line 1,098: Line 1,201:
 
=== number? ===
 
=== number? ===
  
(number? ...)
+
(number? item)
 +
 
 +
Is item a number?
  
 
Example:
 
Example:
Line 1,108: Line 1,213:
 
=== odd? ===
 
=== odd? ===
  
(odd? ...)
+
(odd? number)
 +
 
 +
Is number odd?
  
 
Example:
 
Example:
Line 1,119: Line 1,226:
  
 
(or ...)
 
(or ...)
 +
 +
Or will return #t as soon as it encounters a non-#f in the items (eg, it short circuits without further evaluation of arguments). If no non-#f is encountered, it returns #f.
  
 
Example:
 
Example:
Line 1,128: Line 1,237:
 
=== pair? ===
 
=== pair? ===
  
(pair? ...)
+
(pair? item)
 +
 
 +
A pair is a cons cell. This function tests to see if item is a cons cell.
  
 
Example:
 
Example:
Line 1,134: Line 1,245:
 
<pre>
 
<pre>
 
(pair? (quote ())) => #f
 
(pair? (quote ())) => #f
</pre>
 
  
=== pair? ===
 
 
(pair? ...)
 
 
Example:
 
 
<pre>
 
 
(pair? (cons 1 2)) => #t
 
(pair? (cons 1 2)) => #t
 
</pre>
 
</pre>
 +
 +
Note that '() is not a cons cell; it is a symbol.
  
 
=== parse ===
 
=== parse ===
  
 
(parse ...)
 
(parse ...)
 +
 +
Parse takes an s-expression and returns a parsed version.
  
 
Example:
 
Example:
Line 1,159: Line 1,266:
  
 
(parse-string ...)
 
(parse-string ...)
 +
 +
Parse-string takes a string representing an s-expression and returns the parsed version, like parse.
  
 
Example:
 
Example:
Line 1,165: Line 1,274:
 
(parse-string "(- 7 8)") => (app-aexp (lexical-address-aexp 0 2 - (stdin 1 2 2 1 2 2)) ((lit-aexp 7 (stdin 1 4 4 1 4 4)) (lit-aexp 8 (stdin 1 6 6 1 6 6))) (stdin 1 1 1 1 7 7))
 
(parse-string "(- 7 8)") => (app-aexp (lexical-address-aexp 0 2 - (stdin 1 2 2 1 2 2)) ((lit-aexp 7 (stdin 1 4 4 1 4 4)) (lit-aexp 8 (stdin 1 6 6 1 6 6))) (stdin 1 1 1 1 7 7))
 
</pre>
 
</pre>
 +
 +
The additional numbers are details about line, column, starting and ending place in the file from which this code was received (or "stdin" if it came not from a file.
  
 
=== procedure? ===
 
=== procedure? ===
  
(procedure? ...)
+
(procedure? item)
 +
 
 +
Returns #t if item is a procedure.
  
 
Example:
 
Example:
Line 1,175: Line 1,288:
 
(procedure? procedure?) => #t
 
(procedure? procedure?) => #t
 
</pre>
 
</pre>
 +
 +
=== quote, quasiquote, and unquote ===
 +
 +
<pre>
 +
(quote item)
 +
'item
 +
</pre>
 +
 +
A quoted item (represented by a single-quote) is a symbol (if item is an atom), or is a list of quoted items if item is a list. Literals that are quoted are just the literals.
 +
 +
Examples:
 +
 +
<pre>
 +
'symbol => symbol
 +
'(a list of items) => (a list of items)
 +
</pre>
 +
 +
<pre>
 +
(quasiquote item)
 +
`item
 +
</pre>
 +
 +
Quasiquote (represented by a back-quote) is like a regular quoted item; however, with a quasiquote, unquoted (represented with a comma) items are evaluated.
 +
 +
Examples:
 +
 +
<pre>
 +
(quasiquote (list (unquote (+ 1 2)) 4)) => (list 3 4)
 +
`(list ,(+ 1 2) 4) => (list 3 4)
 +
</pre>
 +
 +
Notice that the (+ 1 2) is evaluated.
  
 
=== quotient ===
 
=== quotient ===
  
(quotient ...)
+
(quotient numerator denominator)
 +
 
 +
Returns the number of times the denominator will go into the numerator.
  
 
Example:
 
Example:
Line 1,188: Line 1,335:
 
=== rac ===
 
=== rac ===
  
(rac ...)
+
(rac ls)
 +
 
 +
Opposite of "car"... returns the last item in a list.
  
 
Example:
 
Example:
Line 1,198: Line 1,347:
 
=== range ===
 
=== range ===
  
(range ...)
+
<pre>
 +
(range stop)
 +
(range start stop)
 +
(range start stop step)
 +
</pre>
 +
 
 +
Returns a range of integers. "stop" never includes the stop number given.
  
 
Example:
 
Example:
Line 1,208: Line 1,363:
 
=== rational ===
 
=== rational ===
  
(rational ...)
+
(rational numerator denominator)
 +
 
 +
Returns the same as what / (divide) would give.
  
 
Example:
 
Example:
Line 1,218: Line 1,375:
 
=== rdc ===
 
=== rdc ===
  
(rdc ...)
+
(rdc ls)
 +
 
 +
Opposite of "cdr"... returns everything in a list but the last item.
  
 
Example:
 
Example:
Line 1,238: Line 1,397:
 
=== remainder ===
 
=== remainder ===
  
(remainder ...)
+
(remainder a b)
 +
 
 +
The remainder, after b is divided into a.
  
 
Example:
 
Example:
Line 1,248: Line 1,409:
 
=== require ===
 
=== require ===
  
(require ...)
+
(require expression)
 +
 
 +
Requires that an expression to be true. If it is not, then it fails, handling control to the fail continuation.
  
 
Example:
 
Example:
Line 1,258: Line 1,421:
 
=== reverse ===
 
=== reverse ===
  
(reverse ...)
+
(reverse ls)
 +
 
 +
Returns a list in reversed order.
  
 
Example:
 
Example:
Line 1,266: Line 1,431:
 
</pre>
 
</pre>
  
=== round-1 ===
+
=== round ===
  
(round-1 ...)
+
(round ...)
 +
 
 +
Rounds a number to the nearest integer.
  
 
Example:
 
Example:
Line 1,274: Line 1,441:
 
<pre>
 
<pre>
 
(round 45.5) => 46
 
(round 45.5) => 46
</pre>
 
  
=== round-2 ===
 
 
(round-2 ...)
 
 
Example:
 
 
<pre>
 
 
(round 45.4) => 45
 
(round 45.4) => 45
 
</pre>
 
</pre>
Line 1,288: Line 1,447:
 
=== set-car! ===
 
=== set-car! ===
  
(set-car! ...)
+
(set-car! ls item)
 +
 
 +
Changes the car of a list to be a new item.
  
 
Example:
 
Example:
Line 1,298: Line 1,459:
 
=== set-cdr! ===
 
=== set-cdr! ===
  
(set-cdr! ...)
+
(set-cdr! ls item)
 +
 
 +
Changes the cdr of a list to be a new item.
  
 
Example:
 
Example:
Line 1,308: Line 1,471:
 
=== snoc ===
 
=== snoc ===
  
(snoc ...)
+
(snoc item ls)
 +
 
 +
Opposite of "cons"... connects an item onto the end of a list.
  
 
Example:
 
Example:
Line 1,318: Line 1,483:
 
=== sort ===
 
=== sort ===
  
(sort ...)
+
(sort comparison-function ls)
 +
 
 +
Takes a comparison-function (such as < or >) and sorts a list using that function. < gives a list in ascending order.
  
 
Example:
 
Example:
Line 1,328: Line 1,495:
 
=== sqrt ===
 
=== sqrt ===
  
(sqrt ...)
+
(sqrt number)
 +
 
 +
Returns the square root of a number.
  
 
Example:
 
Example:
Line 1,338: Line 1,507:
 
=== string ===
 
=== string ===
  
(string ...)
+
(string c ...)
 +
 
 +
Takes the given characters and turns them into a string.
  
 
Example:
 
Example:
Line 1,349: Line 1,520:
  
 
(string->list ...)
 
(string->list ...)
 +
 +
Takes a string, and returns a list of characters.
  
 
Example:
 
Example:
Line 1,359: Line 1,532:
  
 
(string->number ...)
 
(string->number ...)
 +
 +
Takes a string and returns a number.
  
 
Example:
 
Example:
Line 1,369: Line 1,544:
  
 
(string->symbol ...)
 
(string->symbol ...)
 +
 +
Takes a string, and returns a symbol.
  
 
Example:
 
Example:
Line 1,379: Line 1,556:
  
 
(string-append ...)
 
(string-append ...)
 +
 +
Takes the given strings, appends them together, and returns the resulting string.
  
 
Example:
 
Example:
Line 1,388: Line 1,567:
 
=== string-length ===
 
=== string-length ===
  
(string-length ...)
+
(string-length s)
 +
 
 +
Returns the length of a string.
  
 
Example:
 
Example:
Line 1,398: Line 1,579:
 
=== string-ref ===
 
=== string-ref ===
  
(string-ref ...)
+
(string-ref s position)
 +
 
 +
Returns the character in the given position in string s.
  
 
Example:
 
Example:
Line 1,408: Line 1,591:
 
=== string-split ===
 
=== string-split ===
  
(string-split ...)
+
(string-split s c)
 +
 
 +
Splits a string s into strings given a delimiting character c.
  
 
Example:
 
Example:
Line 1,418: Line 1,603:
 
=== string<? ===
 
=== string<? ===
  
(string<? ...)
+
(string<? a b)
 +
 
 +
Is string a less than string b in lexicographic order?
  
 
Example:
 
Example:
  
 
<pre>
 
<pre>
(string<? "a" "b") => #t
+
(string<? "apple" "banana") => #t
 
</pre>
 
</pre>
  
 
=== string=? ===
 
=== string=? ===
  
(string=? ...)
+
(string=? a b)
 +
 
 +
Is string a equal to string b?
  
 
Example:
 
Example:
Line 1,438: Line 1,627:
 
=== string? ===
 
=== string? ===
  
(string? ...)
+
(string? item)
 +
 
 +
Is item a string?
  
 
Example:
 
Example:
Line 1,448: Line 1,639:
 
=== substring ===
 
=== substring ===
  
(substring ...)
+
(substring s start stop)
 +
 
 +
Given a string s, a start position, and stop position, return the substring.
  
 
Example:
 
Example:
Line 1,458: Line 1,651:
 
=== symbol ===
 
=== symbol ===
  
(symbol ...)
+
(symbol s)
 +
 
 +
Given a string s, return a symbol.
  
 
Example:
 
Example:
Line 1,468: Line 1,663:
 
=== symbol->string ===
 
=== symbol->string ===
  
(symbol->string ...)
+
(symbol->string sym)
 +
 
 +
Convert a symbol sym into a string.  
  
 
Example:
 
Example:
Line 1,478: Line 1,675:
 
=== symbol? ===
 
=== symbol? ===
  
(symbol? ...)
+
(symbol? item)
 +
 
 +
Is item a symbol?
  
 
Example:
 
Example:
Line 1,488: Line 1,687:
 
=== typeof ===
 
=== typeof ===
  
(typeof ...)
+
(typeof item)
 +
 
 +
Get the internal type of item. In Python, this will return Python types. In C#, this will return CLR types.
  
 
Example:
 
Example:
Line 1,499: Line 1,700:
  
 
(unparse ...)
 
(unparse ...)
 +
 +
Unparse a parsed expression.
  
 
Example:
 
Example:
Line 1,508: Line 1,711:
 
=== use-lexial-address ===
 
=== use-lexial-address ===
  
(use-lexial-address ...)
+
(use-lexial-address)
 +
(use-lexial-address bool)
 +
 
 +
Get or set the use-lexical-address setting.
  
 
Example:
 
Example:
Line 1,514: Line 1,720:
 
<pre>
 
<pre>
 
(use-lexical-address) => #t
 
(use-lexical-address) => #t
 +
 +
(use-lexical-address #f)
 +
 +
(use-lexical-address) => #f
 
</pre>
 
</pre>
  
=== use-satck-trace ===
+
=== use-stack-trace ===
  
(use-satck-trace ...)
+
(use-stack-trace)
 +
(use-stack-trace bool)
 +
 
 +
Set or get the use-stack-trace setting.
  
 
Example:
 
Example:
Line 1,528: Line 1,741:
 
=== use-tracing ===
 
=== use-tracing ===
  
(use-tracing ...)
+
(use-tracing)
 +
(use-tracing ...)
 +
 
 +
Get or set the use-tracking setting.
  
 
Example:
 
Example:
Line 1,539: Line 1,755:
  
 
(using ...)
 
(using ...)
 +
 +
Use a native library. On Python, you can use Python libraries. In Calico, you can use Calico libraries.
  
 
Example:
 
Example:
Line 1,549: Line 1,767:
  
 
(vector ...)
 
(vector ...)
 +
 +
Create a vector with the elements given.
  
 
Example:
 
Example:
Line 1,556: Line 1,776:
 
</pre>
 
</pre>
  
=== vector->lsit ===
+
=== vector->list ===
  
(vector->lsit ...)
+
(vector->list ...)
 +
 
 +
Convert the vector into a list.
  
 
Example:
 
Example:
Line 1,569: Line 1,791:
  
 
(vector-ref ...)
 
(vector-ref ...)
 +
 +
Get an element from a vector. O(1) operation costs.
  
 
Example:
 
Example:
Line 1,579: Line 1,803:
  
 
(let ...)
 
(let ...)
 +
 +
Create local variables.
  
 
Example:
 
Example:
Line 1,588: Line 1,814:
 
=== vector? ===
 
=== vector? ===
  
(vector? ...)
+
(vector? item)
 +
 
 +
Is item a vector?
  
 
Example:
 
Example:
Line 1,598: Line 1,826:
 
=== (void) ===
 
=== (void) ===
  
((void) ...)
+
(void)
 +
 
 +
Create the void object.
  
 
Example:
 
Example:
Line 1,608: Line 1,838:
 
=== zero? ===
 
=== zero? ===
  
(zero? ...)
+
(zero? number)
 +
 
 +
Is number equal to zero?
  
 
Example:
 
Example:
Line 1,616: Line 1,848:
 
</pre>
 
</pre>
  
=== my-odd ===
+
==== define-syntax ====
 
+
(my-odd ...)
+
 
+
Example:
+
 
+
<pre>
+
(my-odd? 42) => #f
+
</pre>
+
 
+
=== my-even ===
+
 
+
(my-even ...)
+
 
+
Example:
+
 
+
<pre>
+
(my-even? 42) => #t
+
</pre>
+
 
+
=== my-odd ===
+
 
+
(my-odd ...)
+
 
+
Example:
+
 
+
<pre>
+
(my-odd? 43) => #t
+
</pre>
+
 
+
=== my-even ===
+
 
+
(my-even ...)
+
 
+
Example:
+
 
+
<pre>
+
(my-even? 43) => #f
+
</pre>
+
 
+
  
 
<pre>
 
<pre>
Line 1,672: Line 1,865:
  
 
(lambda ...)
 
(lambda ...)
 +
 +
Create a function.
  
 
Example:
 
Example:
Line 1,677: Line 1,872:
 
<pre>
 
<pre>
 
((lambda x x) 1 2 3 4 5) => (1 2 3 4 5)
 
((lambda x x) 1 2 3 4 5) => (1 2 3 4 5)
 +
 
((lambda (x . y) (list x y)) 1 2 3 4 5) => (1 (2 3 4 5))
 
((lambda (x . y) (list x y)) 1 2 3 4 5) => (1 (2 3 4 5))
 +
 
((lambda (a b . z) (list a b z)) 1 2 3 4 5) => (1 2 (3 4 5))
 
((lambda (a b . z) (list a b z)) 1 2 3 4 5) => (1 2 (3 4 5))
 +
 
((lambda (a b . z) (list a b z)) 1 2 3) => (1 2 (3))
 
((lambda (a b . z) (list a b z)) 1 2 3) => (1 2 (3))
 +
 
((lambda (a b . z) (list a b z)) 1 2) => (1 2 ())
 
((lambda (a b . z) (list a b z)) 1 2) => (1 2 ())
 +
 
(try ((lambda (a b . z) (list a b z)) 1) (catch e e "not enough arguments given")) => "not enough arguments given"
 
(try ((lambda (a b . z) (list a b z)) 1) (catch e e "not enough arguments given")) => "not enough arguments given"
 
</pre>
 
</pre>
Line 1,692: Line 1,892:
 
<pre>
 
<pre>
 
(* 10 (call/cc (lambda (k) 4))) => 40
 
(* 10 (call/cc (lambda (k) 4))) => 40
 +
 
(* 10 (call/cc (lambda (k) (+ 1 (k 4))))) => 40
 
(* 10 (call/cc (lambda (k) (+ 1 (k 4))))) => 40
 +
 
(* 10 (call/cc (lambda (k) (+ 1 (call/cc (lambda (j) (+ 2 (j (k 5))))))))) => 50
 
(* 10 (call/cc (lambda (k) (+ 1 (call/cc (lambda (j) (+ 2 (j (k 5))))))))) => 50
 +
 
(* 10 (call/cc (lambda (k) (+ 1 (call/cc (lambda (j) (+ 2 (k (j 5))))))))) => 60
 
(* 10 (call/cc (lambda (k) (+ 1 (call/cc (lambda (j) (+ 2 (k (j 5))))))))) => 60
 
</pre>
 
</pre>
Line 1,711: Line 1,914:
 
# try with a catch-clause: if exception in try-body, catch-clause will catch and provide return value, otherwise body of try provides. If exception in catch-clause will simple raise it.
 
# try with a catch-clause: if exception in try-body, catch-clause will catch and provide return value, otherwise body of try provides. If exception in catch-clause will simple raise it.
 
# try with a finally-clause: finally-clause will run if exception in try-body or not. If there is an exception in the finally, it will raise it.
 
# try with a finally-clause: finally-clause will run if exception in try-body or not. If there is an exception in the finally, it will raise it.
# try with a catch-clause and finally-clause: if an exception in try-body, the catch-clause will run, followed by the finally-clause. If an exception is raised in the catch-clause too, then finally-clause will run, and then raise the catch-exception; if there is an exception raised in the  
+
# try with a catch-clause and finally-clause: if an exception in try-body, the catch-clause will run, followed by the finally-clause. If an exception is raised in the catch-clause too, then finally-clause will run, and then raise the catch-exception; if there is an exception raised in the finally-clause, then it will raise.
finally-clause, then it will raise.
+
  
 
The <sym> of the catch-clause will be bound to the expression raised.
 
The <sym> of the catch-clause will be bound to the expression raised.
Line 1,789: Line 1,991:
 
</pre>
 
</pre>
  
=== or ===
+
(raise ...)
 
+
(or  items)
+
  
 
Example:
 
Example:
  
 
<pre>
 
<pre>
(let ((bool 5)) (or (= bool 4) (= bool 5))) => #t
+
(define div (lambda (x y) (if (= y 0) (raise "division by zero") (/ x y)))) => <void>
(let ((bool 5)) (or (= bool 4) 6)) => 6
+
(let ((bool 5)) (and (= bool 5) (> bool 0) (= bool 4))) => #f
+
 
</pre>
 
</pre>
  
Line 1,819: Line 2,017:
 
<pre>
 
<pre>
 
(let ((r 5)) (record-case (cons (quote banana) (cons (quote orange) (cons (* 2 3) (quote ())))) (apple (a b c) (list c b a r)) ((cherry banana) (a . b) (list b a r)) ((orange) () (quote no)) (else 2 3 4))) => ((6) orange 5)
 
(let ((r 5)) (record-case (cons (quote banana) (cons (quote orange) (cons (* 2 3) (quote ())))) (apple (a b c) (list c b a r)) ((cherry banana) (a . b) (list b a r)) ((orange) () (quote no)) (else 2 3 4))) => ((6) orange 5)
</pre>
 
 
=== raise ===
 
 
(raise ...)
 
 
Example:
 
 
<pre>
 
(define div (lambda (x y) (if (= y 0) (raise "division by zero") (/ x y)))) => <void>
 
 
</pre>
 
</pre>
  
Line 2,084: Line 2,272:
 
  2
 
  2
 
  3
 
  3
 
 
  
 
== Misc ==
 
== Misc ==
Line 2,117: Line 2,303:
 
== Language Interop ==
 
== Language Interop ==
  
Converting from Scheme to Python:
+
Converting from Scheme to Python in Calico:
  
 
<pre>
 
<pre>

Revision as of 02:39, 14 April 2014

Here we will provide documentation for using Calico Scheme.

Calico Scheme is a new implementation of a Scheme-based language for Calico. It implements many core Scheme functions, but also adds some functionality to bring it into line with the other modern languages like Python and Ruby. In can run inside Calico as a DLL, or can run in Python.

This page describes Calico Scheme version 3.0.0.

The Scheme in Python program can be found here:

https://bitbucket.org/ipre/calico/raw/master/languages/Scheme/Scheme/calicoscheme.py

The Scheme in C# can be found in Calico, installed from here:

Calico Download

Contents

Scheme Extensions

  1. Exceptions - implements try/catch/finally
  2. Modules and namespaces - implements namespaces for imports and foreign objects
  3. import libraries written for the Python, or the CLR
  4. Interop - ways for Scheme to interop with other Calico languages

Commands

The following are the functions, syntax, and special forms for Calico Scheme.

%

(% ...)

Modulo gives the amount left over after a divide.

Example:

(% 10 3) => 1

*

(* ...)

Multiply will take a number of arguments and give you the total of all numbers multiplied with each other.

Examples:

(*) => 1

(* 12) => 12

(* 2 3) => 6

(* 2 3 4) => 24

+

(+ ...)

Addition will take a number of arguments and give you the sum of all of the numbers added together.

Example:

(+ 7 8) => 15

-

(- ...)

Subtraction will subtract one number from another.

Example:

(- 5 2) => 3

/

(/ ...)

Divide will divide one number from the previous.

Examples:

(/) => 1

(/ 2) => 1/2

(/ 3 4) => 3/4

<

(< ...)

Less than will return #t or #f as to whether the first number is less than the second.

Example:

(< 5 2) => #f

<=

(<= ...)

Less than or equal than will return #t or #f as to whether the first number is less than, or equal to, the second.

Example:

(<= 5 6) => #t

=

(= ...)

Equality for numbers.

Example:

(= 6 7) => #f

>

(> ...)

Greater than will return #t or #f as to whether the first number is greater than the second.

Example:

(> 9 2) => #t

>=

(>= ...)

Greater than or equals will return #t or #f as to whether the first number is greater than or equal to the second.

Example:

(>= 4 5) => #f

abs

(abs ...)

Returns the absolute value of the number.

Example:

(abs -1) => 1

and

(and ...)

And will return #f as soon as it encounters a #f in the items (eg, it short circuits without further evaluation of arguments). If no #f is encountered, it returns the last item.

Examples:

(and 4 1 2 #t (quote ()) 0) => 0

(and 4 1 2 #t '() 3) => 3

(and 4 1 2 #f '() 0) => #f

append

(append ...)

Append takes a number of lists and combines them. The last item can be an atom, in which case it returns an improper list.

Examples:

(append (quote (1 2 3)) (quote (4 5 6))) => (1 2 3 4 5 6)

(append '(1 2 3) '(4 5 6)) => (1 2 3 4 5 6)

(append '(1 2 3) '(4 5 6) '(7 8 9)) => (1 2 3 4 5 6 7 8 9)

(append '(1 2 3) '(4 5 6) 7) => (1 2 3 4 5 6 . 7)

apply

(apply f args)

Apply takes a function and applies it to a list of arguments. (apply f '(1 2)) operates as if it were written (f 1 2).

Examples:

(apply car (quote ((1)))) => 1

(apply car '((1))) => 1

assq

(assq ...)

Find an association using the eq? operator. Given an item, look it up in a list of pair of associations.

Examples:

(assq 1 (quote ((1 2) (3 4)))) => (1 2)

(assq 1 '((1 2) (3 4))) => (1 2)

assv

(assv ...)

Find an association using the eqv? operator. Given an item, look it up in a list of pair of associations.

Examples:

(assv 1 (quote ((1 2) (3 4)))) => (1 2)

(assv 1 '((1 2) (3 4))) => (1 2)

atom?

(atom? item)

Returns #t if item is an atom.

Example:

(atom? 1) => #t

boolean?

(boolean? item)

Returns #t if item is a boolean (#t or #f) and #f otherwise.

Examples:

(boolean? #t) => #t

(boolean? #f) => #t

car, cdr and related

Given one of these functions and a list, it will return part of the list.

(car ...)

Examples:

(car '(a b)) => a

(car '(a . b)) => a

(car '((a) b) => (a)

(car (quote (((((hello there) this is a test) what is this) another item) in the list))) 
     => ((((hello there) this is a test) what is this) another item)

(cdr ...)

Returns everything in a list, except the car.

Examples:

(cdr '(a b)) => (b)

(cdr '(a . b) => b

(cdr (quote (((((hello there) this is a test) what is this) another item) 1 2 3))) => (1 2 3)

(caaaar list)

Is the same as (car (car (car (car list)))).

Examples:

(caaaar (quote (((((hello there) this is a test) what is this) another item) in the list))) => (hello there)

(caaaar '(((((hello there) this is a test) what is this) another item) in the list)) => (hello there)

(caaadr ...)

Example:

(caaadr (quote (((((hello there) this is a test) what is this) another item) ((((((1 2 3) 4 5 6) 7 8 9) 10 11 12) 13 14 15) 16 17 18)))) => ((((1 2 3) 4 5 6) 7 8 9) 10 11 12)

(caaar ...)

Example:

(caaar (quote (((((hello there) this is a test) what is this) another item) in the list))) => ((hello there) this is a test)

(caadar ...)

Example:

(caadar (quote (((((hello there) this is a test) what is this) (((1 2 3) 4 5 6) 7 8 9) another item) in the list))) => ((1 2 3) 4 5 6)

(caaddr ...)

Example:

(caaddr (quote (((((hello there) this is a test) what is this) (((1 2 3) 4 5 6) 7 8 9) another item) head ((1 2) 3 4) in the list))) => (1 2)

(caadr ...)

Example:

(caadr (quote (((((hello there) this is a test) what is this) (((1 2 3) 4 5 6) 7 8 9) another item) (in this) ((7 8)) the list))) => in

(caar ...)

Example:

(caar (quote (((((hello there) this is a test) what is this) another item) in the list))) => (((hello there) this is a test) what is this)

(cadaar ...)

Example:

(cadaar (quote (((((hello there) this is a test) (what) is this) (yet another) item) in the list))) => (what)

(cadadr ...)

Example:

(cadadr (quote (((((hello there) this is a test) what is this) (yet another) item) (in the) list))) => the

(cadar ...)

Example:

(cadar (quote (((((hello there) this is a test) what is this) (yet another) item) in the list))) => (yet another)

(caddar ...)

Example:

(caddar (quote (((((hello there) this is a test) what is this) another item) in the list))) => item

(cadddr ...)

Example:

(cadddr (quote (((((hello there) this is a test) what is this) another item) in the list))) => list

(caddr ...)

Example:

(caddr (quote (((((hello there) this is a test) what is this) another item) in the list))) => the

(cadr ...)

Example:

(cadr (quote (((((hello there) this is a test) what is this) another item) in the list))) => in

(cdaaar ...)

Example:

(cdaaar (quote (((((hello there) this is a test) what is this) another item)))) => (this is a test)

(cdaadr ...)

Example:

(cdaadr (quote (((((hello there) this is a test) what is this) another item) ((7 8)) 9 10))) => (8)

(cdaar ...)

Example:

(cdaar (quote (((((hello there) this is a test) what is this) another item)))) => (what is this)

(cdadar ...)

Example:

(cdadar (quote (((((hello there) this is a test) what is this) (another two) items)))) => (two)

(cdaddr ...)

Example:

(cdaddr (quote (((((hello there) this is a test) what is this) another item) 1 (2 5) 3 4))) => (5)

(cdadr ...)

Example:

(cdadr (quote (((((hello there) this is a test) what is this) another item) (1 6) (2 5) 3 4))) => (6)

(cdar ...)

Example:

(cdar (quote (((((hello there) this is a test) what is this) another item)))) => (another item)

(cddaar ...)

Example:

(cddaar (quote (((((hello there) this is a test) what is this) another item) 1 (2) 3))) => (is this)

(cddadr ...)

Example:

(cddadr (quote (((((hello there) this is a test) what is this) another item) (7 13) (8 12) 9 10))) => ()

(cddar ...)

Example:

(cddar (quote (((((hello there) this is a test) what is this) another item)))) => (item)

(cdddar ...)

Example:

(cdddar (quote (((((hello there) this is a test) what is this) another item)))) => ()

(cddddr ...)

Example:

(cddddr (quote (((((hello there) this is a test) what is this) another item) 1 2 3 4 5))) => (4 5)

(cdddr ...)

Example:

(cdddr (quote (((((hello there) this is a test) what is this) another item) 1 2 3 4))) => (3 4)

(cddr ...)

Example:

(cddr (quote (((((hello there) this is a test) what is this) another item) 1 2 3))) => (2 3)

case

(case ...)

For use in handling different cases. Returns the first expression that matches. "else" acts as it were #t (always matches).

Examples:

(case 'thing1 
   (thing2 1) 
   (thing1 2))           => 2

(case 'thing1 
   (thing2 1) 
   ((thing1 thing3) 2))  => 2

(case 'thingx 
   (thing2 1) 
   ((thing1 thing3) 2) 
   (else 3))             => 3

cd/current-directory

(cd ...)
(current-directory)

Change/current directory. Given a string, will change to that directory. If you leave out the argument, it returns the current directory.

Example:

(cd)                    => ""
(cd "..")               => moves up one directory

char->integer

(char->integer ...)

Converts a character into an integer.

Example:

(char->integer #\a) => 97

char->string

(char->string ...)

Converts a character into a string.

Example:

(char->string #\b) => "b"

char-alphabetic?

(char-alphabetic? c)

Is c an alphabetic character?

Examples:

(char-alphabetic? #\A) => #t

(char-alphabetic? #\1) => #f

char-numeric?

(char-numeric? c)

Is c an numeric character?

Example:

(char-numeric? #\1) => #t

char-whitespace?

(char-whitespace? ...)

Is c a whitespace (e.g. tab, space, newline) character?

Example:

(char-whitespace? #\t) => #f

(char-whitespace? #\tab) => #t

(char-whitespace? #\newline) => #t

(char-whitespace? #\a) => #f

char=?

(char=? ...)

Returns #t if two characters are the same.

Example:

(char=? #\a #\a) => #t

(char=? #\a #\b) => #f

char?

(char? item)

Is item a character?

Example:

(char? 2) => #f

cond

(cond ...)

Asks a series of questions, and if true, returns the associated expression. "else" acts as if it were "#t".

Example:

(cond 
   (#f 1) 
   (else 2))        => 2

cons

(cons item1 item2)

Constructs a new cons cell by cons-ing item1 onto item2. A proper list ends in the special symbol, '() pronounced "empty list". An improper list ends with a dot, followed by the last item.

Examples:

(cons 1 '())      => (1)

(cons 1 2)        => (1 . 2)

current-environment

(current-environment)

Get the current environment.

Example:

(current-environment)                  => the current environment

current-time

(current-time)

Returns the current time.

Example:

(current-time) => 1397405584.229055

cut

(cut ...)

The (cut) operation will succeed, but cannot be back-tracked afterwards.

Example:

(letrec ((loop (lambda (n) (if (= n 0) (set! var (cut 23)) (loop (- n 1))))) (var 0)) (loop 10) var) => (23)

dict

(dict ...)

Make a dictionary.

Example:

(dict (quote ((1 2) (3 4)))) => none

dir

(dir ...)

Object properties and environment variables.

==> (dir)
(- % * / + < <= = =? > >= abort abs and append apply assq assv atom? boolean? caaaar caaadr caaar caadar 
caaddr caadr caar cadaar cadadr cadar caddar cadddr caddr cadr call/cc call-with-current-continuation 
car case cases cd cdaaar cdaadr cdaar cdadar cdaddr cdadr cdar cddaar cddadr cddar cdddar cddddr cdddr 
cddr cdr char? char=? char-alphabetic? char-numeric? char-whitespace? cond cons current-directory 
current-environment current-time cut debug define-datatype dir display eq? equal? eqv? error eval 
eval-ast even? exit float for-each format get get-member globals import int iter? length let let* letrec 
list list? list->string list->vector list-head list-ref list-tail load make-set make-vector map member 
memq memv newline not null? number? number->string odd? or pair? parse parse-string print printf 
procedure? property quotient range rational read-string record-case remainder require reset-toplevel-env 
reverse safe-print set-car! set-cdr! sort sqrt string string? string<? string=? string->list string->number 
string->symbol string-append string-length string-ref string-split substring symbol symbol? symbol->string 
typeof unparse unparse-procedure use-lexical-address use-tracing using vector vector? vector->list 
vector-ref vector-set! void zero?)
==> (dir my-stuff)
(x y z)

You can also use dir on an object:

(using "Myro")
(dir Myro)

Example:

(length (dir)) => 170

eq?

(eq? ...)

Tests if two object are the same.

Example:

(eq? (quote a) (quote a)) => #t

equal?

(equal? ...)

Tests if two things evaluate to the same value.

Example:

(equal? 1 1.0) => #t

eqv?

(eqv? ...)

Slightly less strict that eq?.

Example:

(eqv? 1 1) => #t

error

(error name message)

Throw an exception. See also the try/catch examples below.

Example:

(try (error (quote a) "message") (catch e e (cadr e))) => "Error in 'a': message"

eval

(eval item)

Evaluate an expression.

Example:

(eval '(+ 1 2)) => 3

eval-ast

(eval-ast ...)

Evaluate an abstract syntax tree.

Example:

(eval-ast (parse (quote (+ 3 4)))) => 7

even?

(even? number)

Returns #t if a number is even.

Example:

(even? 33) => #f

float

(float number)

Returns a floating point version of a number.

Example:

(float 23) => 23.0

for-each

(for-each f sequence)

Maps a function f onto a sequence, but doesn't return anything. Sequence can be a string, list, vector, or other iterator. for-each is used for its side-effects.

Example:

(for-each (lambda (n) (+ n 1)) (quote (1 2 3))) => <void>

format

(format message arg ...)

Formats a message using the following special codes:

  • ~a - "any", prints as display does
  • ~s - "s-expression", prints as write does
  • ~% - newline

Example:

(format "~a ~s ~%" "hello1" "hello2") outputs: hello1 \"hello2\" 

get-stack-trace

(get-stack-trace)

Gets the current stack trace. You can disable stack traces with (use-stack-trace #f).

Example:

(caddr (cadar (get-stack-trace))) => 69

Modules

Modules provide an easy method for structuring hierarchies of libraries and code.

import

(import <string-exp>)
(import <string-exp> '<symbol-exp>)

Examples:

==> (import "my-file.ss")

my-file.ss is a Scheme program file, which itself could have imports.

==> (import "my-file.ss" 'my-stuff)

Loads the file, and puts it in the namespace "my-stuff" accessible through the lookup interface below.

import uses the local environment, while load uses the toplevel-environment.

Lookup

module.name
module.module.name
==> (import "my-file.ss" 'my-stuff)
==> my-stuff.x
5

int

(int number)

Returns an integer form of the number. Note that this rounds to the nearest integer.

Example:

(int 12.8) => 13

integer->char

(integer->char ...)

Converts an integer to a character.

Example:

(integer->char 97) => #\a

iter?

(iter? item)

Returns #t if item is an iterator.

Example:

(iter? 3) => #f

length

(length ls)

Returns the length of a list, ls. Note that this does not recurse into the list, but only counts the toplevel items, even if those are lists.

Example:

(length (quote (1 2 3))) => 3

let

(let ...)

One method of creating local variables.

Example:

(let ((x 1)) x) => 1

let*

(let* ...)

Allows the creation of variables whose value depends on previous variables.

Example:

(let* ((x 1) (y (+ x 1))) y) => 2

In this example, note that y depends on x.

letrec

(letrec ...)

Allows creating recursively defined values.

Example:

(letrec ((loop (lambda (n) 
                  (if (= n 0) 
                      (quote ok) 
                      (loop (- n 1)))))) 
     (loop 10))                              => ok

list

(list ...)

Create a new list by consing the items onto each other, ending in '(), creating a proper list.

Example:

(list 1 2) => (1 2)

list->string

(list->string ...)

Converts a list of characters into a string.

Example:

(list->string (quote (#\1 #\2 #\3))) => "123"

list->vector

(list->vector ...)

Converts a list into a vector. A vector has a fixed length, and can index directly into a position.

Example:

(list->vector (quote (1 2 3))) => [1, 2, 3]

In Python, Scheme uses the Python List as a vector. In C#, Scheme uses an array to represent a vector.

list-ref

(list-ref ...)

A convenient method to get an item from a list. This is no more efficient than a series of car/cdrs.

Example:

(list-ref (quote (1 2 3)) 1) => 2

list?

(list? ...)

Returns #t if an item is a proper list, or the empty list '().

Example:

(list? (quote (1 2 3))) => #t

make-set

(make-set ...)

Creates a list of unique items.

Example:

(sort < (make-set (quote (1 2 3 1 2)))) => (1 2 3)

make-vector

(make-vector size)

Creates a vector of a specific size.

Example:

(make-vector 3) => [0, 0, 0]

map

(map f sequence)

Applies a function to all elements in a sequence, and returns the resulting values in a list.

Example:

(map (lambda (n) (+ n 1)) (range 5)) => (1 2 3 4 5)

member

(member item ls)

Check to see if item is in a list. If it is in the list, return the rest of the list. If not, return #f.

Example:

(member "b" (quote ("a" "b" "c"))) => ("b" "c")

memq

(memq item ls)

Check if item is in ls (like member) but using the eq? operator.

Example:

(memq (quote b) (quote (a b c))) => (b c)

memv

(memv ...)

Check if item is in ls (like member) but using the eqv? operator.

Example:

(memv 2 (quote (1.0 2.0 3.0))) => (2.0 3.0)

not

(not item)

Flips the boolean value of item.

Example:

(not #f) => #t

null?

(null? item)

Checks to see if an item is eq? to the empty list, '().

Example:

(null? (quote ())) => #t

number->string

(number->string ...)

Convert a number into a string.

Example:

(number->string 23) => "23"

number?

(number? item)

Is item a number?

Example:

(number? 23) => #t

odd?

(odd? number)

Is number odd?

Example:

(odd? 45) => #t

or

(or ...)

Or will return #t as soon as it encounters a non-#f in the items (eg, it short circuits without further evaluation of arguments). If no non-#f is encountered, it returns #f.

Example:

(or #t (/ 1 0)) => #t

pair?

(pair? item)

A pair is a cons cell. This function tests to see if item is a cons cell.

Example:

(pair? (quote ())) => #f

(pair? (cons 1 2)) => #t

Note that '() is not a cons cell; it is a symbol.

parse

(parse ...)

Parse takes an s-expression and returns a parsed version.

Example:

(parse (quote (+ 1 2))) => (app-aexp (lexical-address-aexp 0 1 + none) ((lit-aexp 1 none) (lit-aexp 2 none)) none)

parse-string

(parse-string ...)

Parse-string takes a string representing an s-expression and returns the parsed version, like parse.

Example:

(parse-string "(- 7 8)") => (app-aexp (lexical-address-aexp 0 2 - (stdin 1 2 2 1 2 2)) ((lit-aexp 7 (stdin 1 4 4 1 4 4)) (lit-aexp 8 (stdin 1 6 6 1 6 6))) (stdin 1 1 1 1 7 7))

The additional numbers are details about line, column, starting and ending place in the file from which this code was received (or "stdin" if it came not from a file.

procedure?

(procedure? item)

Returns #t if item is a procedure.

Example:

(procedure? procedure?) => #t

quote, quasiquote, and unquote

(quote item)
'item

A quoted item (represented by a single-quote) is a symbol (if item is an atom), or is a list of quoted items if item is a list. Literals that are quoted are just the literals.

Examples:

'symbol => symbol
'(a list of items) => (a list of items)
(quasiquote item)
`item

Quasiquote (represented by a back-quote) is like a regular quoted item; however, with a quasiquote, unquoted (represented with a comma) items are evaluated.

Examples:

(quasiquote (list (unquote (+ 1 2)) 4)) => (list 3 4)
`(list ,(+ 1 2) 4) => (list 3 4)

Notice that the (+ 1 2) is evaluated.

quotient

(quotient numerator denominator)

Returns the number of times the denominator will go into the numerator.

Example:

(quotient 1 4) => 0

rac

(rac ls)

Opposite of "car"... returns the last item in a list.

Example:

(rac (quote (1 2 3))) => 3

range

(range stop)
(range start stop)
(range start stop step)

Returns a range of integers. "stop" never includes the stop number given.

Example:

(range 10) => (0 1 2 3 4 5 6 7 8 9)

rational

(rational numerator denominator)

Returns the same as what / (divide) would give.

Example:

(rational 3 4) => 3/4

rdc

(rdc ls)

Opposite of "cdr"... returns everything in a list but the last item.

Example:

(rdc (quote (1 2 3))) => (1 2)

read-string

(read-string ...)

Example:

(read-string (quote (1 2 3))) => ((pair) ((atom) 1 (stdin 1 2 2 1 2 2)) ((pair) ((atom) 2 (stdin 1 4 4 1 4 4)) ((pair) ((atom) 3 (stdin 1 6 6 1 6 6)) ((atom) () none) none) none) (stdin 1 1 1 1 7 7))

remainder

(remainder a b)

The remainder, after b is divided into a.

Example:

(remainder 1 4) => 1

require

(require expression)

Requires that an expression to be true. If it is not, then it fails, handling control to the fail continuation.

Example:

(require #t) => ok

reverse

(reverse ls)

Returns a list in reversed order.

Example:

(reverse (quote (1 2 3))) => (3 2 1)

round

(round ...)

Rounds a number to the nearest integer.

Example:

(round 45.5) => 46

(round 45.4) => 45

set-car!

(set-car! ls item)

Changes the car of a list to be a new item.

Example:

(let ((x (quote (1 2 3)))) (set-car! x 0) x) => (0 2 3)

set-cdr!

(set-cdr! ls item)

Changes the cdr of a list to be a new item.

Example:

(let ((x (quote (1 2 3)))) (set-cdr! x (quote (3 4))) x) => (1 3 4)

snoc

(snoc item ls)

Opposite of "cons"... connects an item onto the end of a list.

Example:

(snoc 0 (quote (1 2 3))) => (1 2 3 0)

sort

(sort comparison-function ls)

Takes a comparison-function (such as < or >) and sorts a list using that function. < gives a list in ascending order.

Example:

(sort < (quote (3 7 1 2))) => (1 2 3 7)

sqrt

(sqrt number)

Returns the square root of a number.

Example:

(sqrt 3) => 1.7320508075688772

string

(string c ...)

Takes the given characters and turns them into a string.

Example:

(string #\1 #\2) => "12"

string->list

(string->list ...)

Takes a string, and returns a list of characters.

Example:

(string->list "hello world") => (#\h #\e #\l #\l #\o #\  #\w #\o #\r #\l #\d)

string->number

(string->number ...)

Takes a string and returns a number.

Example:

(string->number "12.1") => 12.1

string->symbol

(string->symbol ...)

Takes a string, and returns a symbol.

Example:

(string->symbol "hello") => hello

string-append

(string-append ...)

Takes the given strings, appends them together, and returns the resulting string.

Example:

(string-append "hell" "o") => "hello"

string-length

(string-length s)

Returns the length of a string.

Example:

(string-length "what") => 4

string-ref

(string-ref s position)

Returns the character in the given position in string s.

Example:

(string-ref "what" 2) => #\a

string-split

(string-split s c)

Splits a string s into strings given a delimiting character c.

Example:

(string-split "hello.world" #\.) => ("hello" "world")

string<?

(string<? a b)

Is string a less than string b in lexicographic order?

Example:

(string<? "apple" "banana") => #t

string=?

(string=? a b)

Is string a equal to string b?

Example:

(string=? "a" "b") => #f

string?

(string? item)

Is item a string?

Example:

(string? "hello") => #t

substring

(substring s start stop)

Given a string s, a start position, and stop position, return the substring.

Example:

(substring "hello" 1 3) => "el"

symbol

(symbol s)

Given a string s, return a symbol.

Example:

(symbol "hello") => hello

symbol->string

(symbol->string sym)

Convert a symbol sym into a string.

Example:

(symbol->string (quote hello)) => "hello"

symbol?

(symbol? item)

Is item a symbol?

Example:

(symbol? (quote hello)) => #t

typeof

(typeof item)

Get the internal type of item. In Python, this will return Python types. In C#, this will return CLR types.

Example:

(typeof 23) => <type 'int'>

unparse

(unparse ...)

Unparse a parsed expression.

Example:

(unparse (parse (quote (+ 1 2)))) => (+ 1 2)

use-lexial-address

(use-lexial-address)
(use-lexial-address bool)

Get or set the use-lexical-address setting.

Example:

(use-lexical-address) => #t

(use-lexical-address #f)

(use-lexical-address) => #f

use-stack-trace

(use-stack-trace)
(use-stack-trace bool)

Set or get the use-stack-trace setting.

Example:

(use-stack-trace) => #t

use-tracing

(use-tracing)
(use-tracing ...)

Get or set the use-tracking setting.

Example:

(use-tracing) => #f

using

(using ...)

Use a native library. On Python, you can use Python libraries. In Calico, you can use Calico libraries.

Example:

(try (using "math") (catch e e (using "Graphics"))) => ()

vector

(vector ...)

Create a vector with the elements given.

Example:

(vector 1 2 3) => [1, 2, 3]

vector->list

(vector->list ...)

Convert the vector into a list.

Example:

(vector->list (vector 1 2 3)) => (1 2 3)

vector-ref

(vector-ref ...)

Get an element from a vector. O(1) operation costs.

Example:

(vector-ref (vector 1 2 3) 2) => 3

let

(let ...)

Create local variables.

Example:

(let ((v (vector 1 2 3))) (vector-set! v 2 (quote a)) v) => [1, 2, a]

vector?

(vector? item)

Is item a vector?

Example:

(vector? (vector)) => #t

(void)

(void)

Create the void object.

Example:

(void) => <void>

zero?

(zero? number)

Is number equal to zero?

Example:

(zero? 0.0) => #t

define-syntax

(begin (define hello 0) (for 5 times do (set! hello (+ hello 1))) hello) => 5
(for sym in (quote (a b c d)) do (define x 1) (set! x sym) x) => done
(for n in (range 10 20 2) do n) => done
(for n at (i j) in matrix2d do (list n (quote coords:) i j)) => done
(for n at (i j k) in matrix3d do (list n (quote coords:) i j k)) => done
(! 5) => 120
(nth 10 facts) => 3628800
(nth 20 fibs) => 10946
(first 30 fibs) => (1 1 2 3 5 8 13 21 34 55 89 144 233 377 610 987 1597 2584 4181 6765 10946 17711 28657 46368 75025 121393 196418 317811 514229 832040)

lambda

(lambda ...)

Create a function.

Example:

((lambda x x) 1 2 3 4 5) => (1 2 3 4 5)

((lambda (x . y) (list x y)) 1 2 3 4 5) => (1 (2 3 4 5))

((lambda (a b . z) (list a b z)) 1 2 3 4 5) => (1 2 (3 4 5))

((lambda (a b . z) (list a b z)) 1 2 3) => (1 2 (3))

((lambda (a b . z) (list a b z)) 1 2) => (1 2 ())

(try ((lambda (a b . z) (list a b z)) 1) (catch e e "not enough arguments given")) => "not enough arguments given"

call/cc

(call/cc procedure)

Examples:

(* 10 (call/cc (lambda (k) 4))) => 40

(* 10 (call/cc (lambda (k) (+ 1 (k 4))))) => 40

(* 10 (call/cc (lambda (k) (+ 1 (call/cc (lambda (j) (+ 2 (j (k 5))))))))) => 50

(* 10 (call/cc (lambda (k) (+ 1 (call/cc (lambda (j) (+ 2 (k (j 5))))))))) => 60

Exceptions

(raise <exp>)
(try <exp>...)
(try <exp>... (catch <sym> <exp>...))
(try <exp>... (finally <exp>...))
(try <exp>... (catch <sym> <exp>...) (finally <exp>...))

There are four main forms of try:

  1. try alone: has no effect---doesn't catch exceptions
  2. try with a catch-clause: if exception in try-body, catch-clause will catch and provide return value, otherwise body of try provides. If exception in catch-clause will simple raise it.
  3. try with a finally-clause: finally-clause will run if exception in try-body or not. If there is an exception in the finally, it will raise it.
  4. try with a catch-clause and finally-clause: if an exception in try-body, the catch-clause will run, followed by the finally-clause. If an exception is raised in the catch-clause too, then finally-clause will run, and then raise the catch-exception; if there is an exception raised in the finally-clause, then it will raise.

The <sym> of the catch-clause will be bound to the expression raised.

Examples

==> 

> (try x)
(uncaught exception: "unbound variable x")
==> "(try x (catch e e))"
"unbound variable x"
==> "(try x (catch e (raise e)))"
(uncaught exception: "unbound variable x")
==> "(try x (finally 'hi))"
hi 
(uncaught exception: "unbound variable x")
==> "(try x (catch e 1 2 3 4 (finally 'hi))"
hi 
4

try, catch, raise, finally

Examples:

(try (let loop ((n 5)) n (if (= n 0) (raise (quote blastoff!))) (loop (- n 1))) (catch e e)) => blastoff!

(try 3) => 3

(try 3 (finally (quote yes) 4)) => 3

(try (raise (quote yes)) (catch e e)) => yes

(try (try (raise (quote yes))) (catch e e)) => yes

(try (try (begin (quote one) (raise (quote oops)) (quote two))) (catch e e)) => oops

(* 10 (try (begin (quote one) (raise (quote oops)) (quote two)) (catch ex 3 4))) => 40

(* 10 (try (begin (quote one) (quote two) 5) (catch ex 3 4))) => 50

(* 10 (try (begin (quote one) (raise (quote oops)) 5) (catch ex (list (quote ex:) ex) 4))) => 40

(try (* 10 (try (begin (quote one) (raise (quote oops)) 5) (catch ex (list (quote ex:) ex) (raise ex) 4))) (catch e e)) => oops

(try (* 10 (try (begin (quote one) (raise (quote oops)) 5) (catch ex (list (quote ex:) ex) (raise ex) 4) (finally (quote two) 7))) (catch e e)) => oops

(try (* 10 (try (begin (quote one) (raise (quote oops)) 5) (catch ex (list (quote ex:) ex) (raise (quote bar)) 4))) (catch x (quote hello) 77)) => 77

(try 3 (finally (quote hi) 4)) => 3

(try (div 10 0) (catch e e)) => "division by zero"

(try (let ((x (try (div 10 0)))) x) (catch e e)) => "division by zero"

(let ((x (try (div 10 2) (catch e -1)))) x) => 5

(let ((x (try (div 10 0) (catch e -1)))) x) => -1

(let ((x (try (div 10 2) (catch e -1) (finally (quote closing-files) 42)))) x) => 5

(let ((x (try (div 10 0) (catch e -1) (finally (quote closing-files) 42)))) x) => -1

(let ((x (try (div 10 2) (finally (quote closing-files) 42)))) x) => 5

(try (let ((x (try (div 10 0) (catch e -1 (raise (quote foo))) (finally (quote closing-files) 42)))) x) (catch e e)) => foo

(try (let ((x (try (div 10 0) (catch e -1 (raise (quote foo))) (finally (quote closing-files) (raise (quote ack)) 42)))) x) (catch e e)) => ack

(try (let ((x (try (div 10 0) (catch e -1 (raise (quote foo))) (finally (quote closing-files) (raise (quote ack)) 42)))) x) (catch e (if (equal? e (quote ack)) 99 (raise (quote doug)))) (finally (quote closing-outer-files))) => 99

(try (try (let ((x (try (div 10 0) (catch e -1 (raise (quote foo))) (finally (quote closing-files) (raise (quote ack)) 42)))) x) (catch e (if (equal? e (quote foo)) 99 (raise (quote doug)))) (finally (quote closing-outer-files))) (catch e e)) => doug

(raise ...)

Example:

(define div (lambda (x y) (if (= y 0) (raise "division by zero") (/ x y)))) => <void>

case

(case ...)

Example:

(let ((r 5)) (case (quote banana) (apple (quote no)) ((cherry banana) 1 2 r) (else (quote no)))) => 5

record-case

(record-case ...)

Example:

(let ((r 5)) (record-case (cons (quote banana) (cons (quote orange) (cons (* 2 3) (quote ())))) (apple (a b c) (list c b a r)) ((cherry banana) (a . b) (list b a r)) ((orange) () (quote no)) (else 2 3 4))) => ((6) orange 5)

div

(div ...)

Example:

(div 10 2) => 5

define-datatype

(define-datatype ...)

Example:

(define-datatype lc-exp lc-exp?
  (var-exp 
   (var symbol?))
  (lambda-exp 
   (bound-var symbol?)
   (body lc-exp?))
  (app-exp
   (rator lc-exp?)
   (rand lc-exp?)))

That defines the following:

lc-exp?
var-exp
lambda-exp
app-exp
(var-exp (quote a)) => ()
(lambda-exp (quote a) (var-exp (quote a))) => ()
(app-exp (lambda-exp (quote a) (var-exp (quote a))) (var-exp (quote a))) => ()
(define un-parse
  (lambda (exp)
    (cases lc-exp exp
       (var-exp (var) var)
       (lambda-exp (bound-var body) (list bound-var body))
       (app-exp (rator rand) (list rator rand)))))

(un-parse (var-exp (quote a))) => a
(un-parse (lambda-exp (quote a) (var-exp (quote a)))) => (a (var-exp a))
(un-parse (app-exp (lambda-exp (quote a) (var-exp (quote a))) (var-exp (quote a)))) => ((lambda-exp a (var-exp a)) (var-exp a))

choose/fail

Calico Scheme also contains a non-deterministic search with back-tracking. To use this, you select choice-points using the keyword "choose" with arguments, set requirements using the keyword "require", and fail using "(choose)". For example, to automatically find two numbers that sum to seven:

(define sum-to-seven
  (lambda ()
    (let ((num1 (choose 0 1 2 3 4 5 6 7 8 9))
          (num2 (choose 0 1 2 3 4 5 6 7 8 9)))
      (require (= (+ num1 num2) 7))
      (printf "The numbers are ~s ~s\n" num1 num2))))

Then, you can let Scheme do the searching for you:

scheme>>> (sum-to-seven)
The numbers are 0 7
Done

If you don't like that result, you can force Scheme back to any choice-points to make a different choice:

scheme>>> (choose)
The numbers are 1 6
Done

This can continue until there are no more choices left.

See menu -> File -> Examples -> Scheme -> choose-examples.ss for more examples.

scheme>>> (choose)
The numbers are 7 0
Done
(define distinct? 
  (lambda (nums) 
    (or (null? nums) 
	(null? (cdr nums)) 
	(and (not (member (car nums) (cdr nums))) 
	     (distinct? (cdr nums))))))
(define floors2 
  (lambda () 
    (let ((baker (choose 1 2 3 4 5))) 
      (require (not (= baker 5))) 
      (let ((fletcher (choose 1 2 3 4 5))) 
	(require (not (= fletcher 5))) 
	(require (not (= fletcher 1))) 
	(let ((cooper (choose 1 2 3 4 5))) 
	  (require (not (= cooper 1))) 
	  (require (not (= (abs (- fletcher cooper)) 1))) 
	  (let ((smith (choose 1 2 3 4 5))) 
	    (require (not (= (abs (- smith fletcher)) 1))) 
	    (let ((miller (choose 1 2 3 4 5))) 
	      (require (> miller cooper)) 
	      (require (distinct? (list baker cooper fletcher miller smith))) 
	      (list (list (quote baker:) baker) 
		    (list (quote cooper:) cooper) 
		    (list (quote fletcher:) fletcher) 
		    (list (quote miller:) miller) 
		    (list (quote smith:) smith)))))))))
(floors2) => ((baker: 3) (cooper: 2) (fletcher: 4) (miller: 5) (smith: 1))

define-syntax

define-syntax is used to change the semantics of Scheme in a manner not possible with regular functions. For example, imagine that you wanted to time a particular function call. To time a function, you can do:

(let ((start (current-time)))
  (fact 5)
  (- (current-time) start))

If you tried to define a function time such that you could call it like:

(time (fact 5))

then, unfortunately, you would evaluate (fact 5) before you could do anything in the function time. You could call it like:

(time fact 5)

but that looks a bit strange. Perhaps a more natural way would be to just change the semantics of Scheme to allow (time (fact 5)). Scheme makes that easy with define-sytnax:

(define-syntax time 
  [(time ?exp) (let ((start (current-time)))
		 ?exp
		 (- (current-time) start))])

Now, you can call it like:

(time (fact 5))

and you get the correct answer.

define-syntax takes a list of two items: a template, and a response. If the template matches, then you evaluate the response. In this example, (time ?exp) matches, so the system will record the start time, evaluate the ?exp, and then return the time minus the start time.

Calico Scheme uses this simple, but powerful pattern matcher to implement define-case. Here is a more complex example: for.

(define-syntax for
  [(for ?exp times do . ?bodies)
   (for-repeat ?exp (lambda () . ?bodies))]
  [(for ?var in ?exp do . ?bodies)
   (for-iterate1 ?exp (lambda (?var) . ?bodies))]
  [(for ?var at (?i) in ?exp do . ?bodies)
   (for-iterate2 0 ?exp (lambda (?var ?i) . ?bodies))]
  [(for ?var at (?i ?j . ?rest) in ?exp do . ?bodies)
   (for ?var at (?i) in ?exp do
     (for ?var at (?j . ?rest) in ?var do . ?bodies))])

In this example, define-syntax creates a for function with 4 forms:

(for 4 times do (function ...))

(for x in '(1 2 3) do (function ...))

(for x at (0) in '(1 2 3) do (function ...))

(for x at (0 1 2) in (range 10) do (function ...))
(define-syntax collect
  [(collect ?exp for ?var in ?list)
   (filter-map (lambda (?var) ?exp) (lambda (?var) #t) ?list)]
  [(collect ?exp for ?var in ?list if ?condition)
   (filter-map (lambda (?var) ?exp) (lambda (?var) ?condition) ?list)])

(collect (* n n) for n in (range 10)) => (0 1 4 9 16 25 36 49 64 81)

(collect (* n n) for n in (range 5 20 3)) => (25 64 121 196 289)

(collect (* n n) for n in (range 10) if (> n 5)) => (36 49 64 81)

Calico Libraries

You can use any of the Calico libraries:

scheme> (using "DLLName")
scheme> (DLLName.Class arg1 arg2)

For example, you can use Scheme to do art or control robots:

(using "Myro")
(Myro.init "sim")
(Myro.joystick)

Interop

There is a special object in the environment, calico. It has access to a variety of Calico functions. See Calico: calico object for more details.

Use the define! to put a variable in the global Calico namespace.

scheme> (define! x 8)
python> x
8

Wrap a function for use by other Calico languages:

scheme> (func (lambda (a b) (+ a b)))

Combine for cross-language interoperation:

 scheme> (define fact (lambda (n) (if (= n 1) 1 (* n (fact (- n 1))))))
 scheme> (define! factorial (func fact))
 python> factorial(5)
 120

Be careful not to wrap the func around the part that is called recursively, or you will destroy the tail-call optimization.

Iterators

Strings, vectors, and lists all work with map and for-each.

==> (map display "123")
123(void void void)
==> (for-each (lambda (v) (printf "~a\n" v)) (range 3))
1
2
3

Misc

typeof will give you the .NET type of a value:

==> (typeof 1)
System.Int32
==> (typeof 238762372632732736)
Microsoft.Scripting.Math.BigInteger
==> (typeof 1/5)                
Rational
==> (cd "/path/to/folder")
==> (cd)
"/path/to/folder"
==> (import "file.ss" 'F)
==> (set! F.x 45)
==> (current-environment)
#<environment>
==> (remainder 4 5)
==> (quotient 6 4)
==> (dir (current-environment))
==> (make-set '(1 1 2 3 4 5))
==> (using "Myro")
==> (dir Myro.robot)

Language Interop

Converting from Scheme to Python in Calico:

scheme> (define pylist (calico.Evaluate "lambda *args: list(args)" "python"))
Ok
scheme> (define pytuple (calico.Evaluate "lambda *args: args" "python"))
Ok
scheme> (pylist 1 2 3)
[1, 2, 3]
scheme> (pytuple 1 2 3)
(1, 2, 3)

Converting from Python to Scheme

scheme> (define pylist2list
           (lambda (args)
              (map (lambda (i) i) args)))
Ok
scheme> (pylist2list (pylist 1 2 3))
(1 2 3)
scheme> (pylist2list (pytuple 1 2 3))
(1 2 3)

References

Calico

  1. CalicoDevelopment - plans and details for Calico development
  2. http://www.scheme.com/tspl4/ - The Scheme Programming Language, 4th edition

For Developers