||KRC legacy prelude, used with EMAS KRC ||Copyright (c) D. A. Turner 1981 All rights reserved ||See file COPYING for terms abs :- takes the absolute value of a number, e.g. abs (-3) is 3; abs x = x, x >= 0 = -x and :- applied to a list of truthvalues, takes the logical conjunction; and = fold '&' "TRUE" append :- applied to a list of lists, joins them into a single list with `++'; append = fold '++' [] assoc :- takes a list of [key, value] pairs and a value, returning the associated key; assoc ([a,b]:x) a' = b, a == a' = assoc x a' char :- predicate, true on strings of size one, false otherwise (defined in machine code); cjustify :- applied to a number and a string, centre justifies the string in a field of the specified width; cjustify n x = cjustify' (n - printwidth x) x cjustify' n x = [spaces (n / 2),x,spaces ((n + 1) / 2)] coalesce :- takes a list of lists and merges them into a single list, by repeated use of "interleave" - differs from "append" in that it will work even if several of the lists are infinite (indeed even if there are an infinite number of infinite lists!); coalesce = fold interleave [] code :- converts a character to its ascii code number (defined in machine code); compose :- takes a list of functions and composes them with `.' to make a single function; compose = fold '.' I concat :- takes a list of strings and concatenates them into one big string (defined in machine code); cons :- adds an element to the front of a list; cons a x = a:x decode :- converts an integer to the character of that ascii number (defined in machine code); digit :- predicate, true on single digit strings; digit x = char x & "0" <= x <= "9" digitval :- returns the numeric value of a digit; digitval x = code x - code "0", digit x drop :- `drop n x' returns list x without its first n elements; drop 0 x = x drop n [] = [] drop n (a:x) = drop (n - 1) x even :- predicate, true on even numbers; even x = x % 2 == 0 explode :- explodes a string into a list of its constituent characters (defined in machine code); false = "FALSE" filter :- applied to a predicate and a list returns a list of the elements for which the predicate takes value "TRUE"; filter f x = {a|a<-x;f a} fold :- folds a list to the right with a given operator and start value. Example: foldr op r [a,b,c] = op a (op b (op c r)); fold op s [] = s fold op s (a:x) = op a (fold op s x) for :- `for a b f' maps function f over the list of numbers [a..b]; for a b f = map f [a..b] function :- type testing predicate (defined in machine code); hd :- applied to a non empty list, returns its first element; hd (a:x) = a I :- the identity function, applied to any object it returns it; I x = x insert :- used by sort, inserts a new value into a sorted list in the correct position to maintain ascending order; insert a [] = [a] insert a (b:x) = a:b:x, a <= b = b:insert a x interleave :- merges two lists by taking members from them alternately; interleave (a:x) y = a:interleave y x interleave [] y = y intersection :- takes a list of lists and returns a list of elements common to all; intersection [x] = x intersection (x:xx) = filter (member x) (intersection xx) lay :- applied to a list formats it to have one element per line when printed with !; lay [] = [] lay (a:x) = show a:nl:lay x layn :- similar to `lay', but produces output with numbered lines; layn x = layn' 1 x layn' :- (layn' n x) formats list x one element per line with lines numbered from n; layn' n [] = [] layn' n (a:x) = rjustify 4 n:") ":show a:nl:layn' (n + 1) x letter :- predicate, true on single letter strings; letter x = uppercase x | lowercase x limit :- finds the fixed point, if any, of a function repeatedly applied to an initial value; limit f x = limit f (f x), f x \= x = x list :- type testing predicate (defined in machine code); listdiff :- defines the action of the "--" operator; listdiff [] y = [] listdiff x [] = x listdiff (a:x) (b:y) = listdiff x y, a == b = listdiff (a:listdiff x [b]) y ljustify :- applied to a number and a string, left justifies the string in a field of the specified width; ljustify n x = [x,spaces (n - printwidth x)] lowercase :- predicate, true on lowercase letters; lowercase x = char x & code "a" <= code x <= code "z" map :- applied to a function and a list returns the list obtained by applying the function to each element; map f x = {f a|a<-x} max :- returns the largest element, under `>', of a list of numbers or strings; max [a] = a max [a,b] = a, a >= b = b max (a:x) = max [a,max x] member :- applied to a list and a value returns "TRUE" or "FALSE" as the value is or not present in the list; member [] a = "FALSE" member (a:x) b = a == b | member x b min :- returns the least element, under `<', of a list of numbers or strings; min = hd . sort mkset :- applied to a list returns the list with duplicate elements removed; mkset x = mkset' x [] mkset' [] y = [] mkset' (a:x) y = mkset' x y, member y a = a:mkset' x (a:y) neg :- a function with same action as prefix `-'; neg x = -x nl :- newline; nl = decode 10 not :- a function with same action as prefix `\'; not x = \x np :- newpage; np = decode 12 number :- type testing predicate (defined in machine code); odd :- predicate, true on odd numbers; odd x = \even x or :- applied to a list of truthvalues, takes their disjunction; or = fold '|' "FALSE" perms :- returns a list of all possible permutations of a given list; perms [] = [[]] perms x = {a:p|a<-x;p<-perms (x -- [a])} powerset :- given a set, represented by a list of elements, returns a list of all the subsets that can be formed from it; powerset [] = [[]] powerset (a:x) = powerset' a (powerset x) powerset' :- auxiliary function used by powerset; powerset' a p = p ++ {a:y|y<-p} printwidth :- for any x, gives width of x on printing (with "!") (defined in machine code); product :- applied to list of numbers returns their product; product = fold '*' 1 quote :- quotation mark; quote = decode 34 read :- takes a file or device name and returns a list of characters (defined in machine code); reverse :- applied to a list returns a list of the same elements in reverse order; reverse [] = [] reverse (a:x) = reverse x ++ [a] rjustify :- applied to a number and a string, right justifies the string in a field of the specified width; rjustify n x = [spaces (n - printwidth x),x] show :- show :- applied to any (non-function) value formats it to show its structure when printed with !; show x = "nl", x == nl = "np", x == np = "tab", x == tab = "vt", x == vt = [quote,x,quote], string x = ["[",show' x,"]"], list x = x show' [] = [] show' [a] = [show a] show' (a:x) = show a:",":show' x sort :- sort :- of a list of numbers or strings returns an ordered list of the same elements; sort [] = [] sort (a:x) = insert a (sort x) sp :- single space; sp = " " spaces :- applied to a number returns a list of that many spaces; spaces 0 = [] spaces n = " ":spaces (n - 1) string :- type testing predicate (defined in machine code); sum :- applied to list of numbers returns their sum; sum = fold '+' 0 tab :- single tab; tab = decode 9 take :- take :- `take n x' returns a list of the first n elements of list x; take 0 x = [] take n [] = [] take n (a:x) = a:take (n - 1) x tl :- applied to a non-empty list returns it without the first element; tl (a:x) = x true = "TRUE" union :- returns the union of a list of lists, representing sets; union = mkset . coalesce update :- `update f key value' is a function that returns `value' when applied to key and on other inputs behaves as function f; update f x y z = y, z == x = f z uppercase :- predicate, true on uppercase letters; uppercase x = char x & code "A" <= code x <= code "Z" vt :- vertical tab; vt = decode 11 write :- used to mark items to be sent to a file on output with ! write "filename" x where x is any KRC data item (defined in machine code); zip :- applied to a list of lists, returns their transpose (as in matrix transpose, rows and columns interchanged). Example zip [[1,2,3],[4,5,6]] = [[1,4],[2,5],[3,6]]; zip x = [], hd x == [] = map hd x:zip (map tl x)