other module/example?
How will wiki and blog be affected if at all?
This section allows you to view all posts made by this member. Note that you can only see posts made in areas you currently have access to.
Show posts Menu
;; usage: newlisp compile.lsp executable source.lsp
;; Note: requires link.lsp in the same directory.
;; To compile.lsp rename this file to cnl.lsp
;; and copy and paste "link.lsp" inline replacing
;; (load "link.lsp") below with this inline copy.
;; Now you can compile cnl.lsp with:
;;
;; newlisp compile.lsp cnl[.exe] cnl.lsp
;;
;; You can then use cnl like this:
;;
;; cnl executable source
(load "link.lsp")
(set 'os (& 0x0F (last (sys-info))))
(if (find os '(5 6))
(set 'newlisp "newlisp.exe")
(set 'newlisp "newlisp"))
(set 'argv (main-args))
(if (starts-with (first argv) "newlisp")
(set 'offset 1)
(set 'offset 0))
(if (< (length argv) (+ 3 offset))
(begin
(println)
(print "Usage: " (first argv))
(if (> offset 0)
(print " compile.lsp"))
(println " executable source.lsp")
(exit)))
(set 'executable-file (nth (+ 1 offset) argv))
(set 'source-file (nth (+ 2 offset) argv))
(link newlisp executable-file source-file)
(exit)
;; A Unix like cron scheduler for Windows.
;; by John W. Small
;; usage: newlisp cron.lsp [crontab]
;; crontab file:
;;
;; # This is a comment!
;;
;; # Fields:
;;
;; # minute: 0-59
;; # hour: 0-23
;; # day of the month: 1-31
;; # month of the year: 1-12
;; # day of the week: 0-6 with Sunday = 0
;;
;; # Field may contain a number, i.e. 5
;; # A comma separated (no spaces), i.e. 5,6,7
;; # A range (no spaces), i.e. 5-7
;; # an asterisk, i.e. * meaning all values
;;
;; # Scheduled tasks
;; # min hour monthday month weekday command arg
;;
;; 0 22 * * * start e:/backup/nightly.bat
;; 30 23 * * 5 start e:/backup/weekly.bat
(set 'crontab "crontab")
(set 'crontab-last-modified nil)
(set 'crontab-contents nil)
; find crontab
(let ((argv (main-args)))
(let ((argc (length argv)))
(if (> argc (if (= (first argv) "newlisp") 2 1))
(set 'crontab (nth (- argc 1) argv)))))
(if (not (file? crontab))
(begin
(println)
(println "crontab not found: " crontab)
(exit)))
(define (set-daylight-corrected-timezone)
(set 'daylight-corrected-timezone (- 0 (last (now))))
(let ((local-date (parse (date (apply date-value (now))) {s+} 0)))
(let ((local-time (nth 3 local-date)))
(let ((local-hour (integer (first (parse local-time ":"))))
(local-timezone-hour (nth 3 (now daylight-corrected-timezone))))
(set 'daylight-corrected-timezone
(+ daylight-corrected-timezone
(* 60 (- local-hour local-timezone-hour))))))))
; re-load crontab if changed
(define (crontab-refresh , crontab-file row-idx line fields)
(set-daylight-corrected-timezone)
(let ((last-modified (nth 6 (file-info crontab))))
(if (or (not crontab-last-modified)
(> last-modified crontab-last-modified))
(begin
(println)
(println (date (apply date-value (now))))
(println "Loading crontab: " crontab)
(set 'crontab-last-modified last-modified)
(set 'crontab-file (open crontab "read"))
(set 'crontab-contents '())
(set 'row-idx 0)
(while (read-line crontab-file)
(set 'line (trim (current-line)))
(set 'fields (filter (fn (f) (> (length f) 0))
(parse line {s+} 0)))
(if (and (> (length fields) 0)
(!= (nth 0 (first fields)) "#"))
(begin
(push fields crontab-contents row-idx)
(inc 'row-idx))))
(close crontab-file))))
crontab-contents)
(define (alarmed? scheduled actual , after before)
(or (= scheduled "*")
(cond
((find "," scheduled)
(find actual (map integer (parse scheduled ","))))
((find "-" scheduled)
(map set '(after before) (map integer (parse scheduled "-")))
(and (>= actual after) (<= actual before)))
(true
(= actual (integer scheduled))))))
;; list-let usage:
;;
;; (list-let '(1 2 3) (x y z)
;; (println x y z)
;; (list x y z))
(define-macro (list-let _values _vars)
(let ((bindings (map (fn (_var _value) (list _var _value))
_vars (eval _values)))
(body (rest (rest (args)))))
(eval (cons 'let (cons bindings body)))))
(while (crontab-refresh)
(list-let (now daylight-corrected-timezone)
(year month day hour minute sec micsec doy dow tz)
(dec 'dow)
(dolist (crontab-record crontab-contents)
(list-let crontab-record
(t_minute t_hour t_day t_month t_dow t_cmd t_arg)
(if (and
(alarmed? t_month month)
(alarmed? t_day day)
(alarmed? t_dow dow)
(alarmed? t_hour hour)
(alarmed? t_minute minute))
(if (file? t_arg)
(begin
(println)
(println (date (apply date-value (now))))
(println "Alarm on: " (join crontab-record " "))
(println t_cmd " " t_arg)
(exec t_arg)))))))
(sleep 60000))
(exit)
(define-macro (list-let _values _vars)
(let ((bindings (map (fn (_var _value) (list _var _value))
_vars (eval _values)))
(body (rest (rest (args)))))
(eval (cons 'let (cons bindings body)))))
(list-let '("John Doe" "Acme Widgets" "1-800-123-4567")
(name company phone)
(list company phone name))
;; => ("Acme Widgets" "1-800-123-4567" "John Doe")
(define-macro (alist-let _alist _var-alias-defaults)
(let ((_alist (eval _alist)))
(let ((bindings
(map (fn (_var-alias-default , _value _alias _default)
(if (list? _var-alias-default)
(begin
(set '_value (assoc (first _var-alias-default) _alist))
(set '_alias (first (rest _var-alias-default)))
(set '_default (rest (rest _var-alias-default))))
(begin
(set '_alias _var-alias-default)
(set '_value (assoc _var-alias-default _alist))))
(if (list? _value)
(if (> (length _value) 2)
(list _alias (cons 'list (rest _value)))
(list _alias (first (rest _value))))
(list _alias _value)))
_var-alias-defaults))
(body (rest (rest (args)))))
(eval (cons 'let (cons bindings body))))))
(alist-let '((name "John" "Doe") (company "Acme Widgets") (phone "1-800-123-4567"))
(phone (name name1) (country country1 "USA") (company company1))
(list company1 phone name1 country1))
;; => ("Acme Widgets" "1-800-123-4567" ("John" "Doe") "USA")
(define z 3)
(define foo
(let ((y 2))
(expand (lambda (x) (list x y z)) 'y 'z)))
(foo 1) ;; ==> (1 2 3)
> foo
(lambda (x) (list x 2 3))
(define z 3)
(define foo
(expand-let
(lambda (x) (list x y z))
(y 2) (z z)))
(define-macro (expand-let )
(eval
(cons 'let
(cons (rest (args))
(list (cons 'expand
(cons (first (args))
(map (fn (arg) (apply quote (list (first arg))))
(rest (args))))))))))
(define (foo x y) (+ x y))
> (fn-let foo (x 1))
(lambda (y) (let ((x 1)) (+ x y)))
(define-macro (fn-let _f )
(let ((fargs (first (eval _f)))
(body (rest (eval _f)))
(cargs (map (fn (k-v) (first k-v)) (rest (args))))
(bindings (map (fn (k-v)
(list (first k-v)
(eval (last k-v))))
(rest (args)))))
(let ((new-fargs (difference fargs cargs))
(new-body (cons 'let (cons bindings body))))
(eval
(expand '(lambda new-fargs new-body)
'new-fargs 'new-body)))))
(define (eval-args _args)
(map (fn (arg) (eval arg)) _args))
(define-macro (curry _f )
(let ((f (eval _f))
(cargs (eval-args (rest (args)))))
(expand
(lambda-macro ( )
(apply f (append (quote cargs) (eval-args (args)))))
'f 'cargs)))
(define-macro (rcurry _f )
(let ((f (eval _f))
(cargs (eval-args (rest (args)))))
(expand
(lambda-macro ( )
(apply f (append (eval-args (args)) (quote cargs))))
'f 'cargs)))
(define (math-series op init f a a++ >b?)
(if (>b? a)
init
(math-series op (op init (f a)) f (a++ a) a++ >b?)))
(define (summation f a step b)
(math-series add 0 f a (curry add step) (rcurry > b)))
(define (sigma f a b)
(summation f a 1 b))
(sigma add 1 3) ;; ==> 6
(define (step-integral dx f a)
(mul dx (f a)))
(define (integrate f a b dx)
(summation (fn-let step-integral (dx dx) (f f)) a dx b))
(define (line m b x)
(add (mul m x) b))
(integrate (fn-let line (m 1) (b 0)) 0 1 0.01) ;; 0.495 ...
(define (product f a b)
(math-series mul 1 f a (curry + 1) (rcurry > b)))
(define (factorial n)
(product mul 1 n))
(factorial 5) ;; ==> 120
(sigma (lambda (n) (/ 1.0 (factorial n))) 0 20)
;; ==> 2.7182 ...
(define-macro (disjoin )
(let ((_f (eval (first (args))))
(_fs (eval-args (rest (args)))))
(expand
(lambda (arg , result f fs)
(set 'result false)
(set 'f _f)
(set 'fs (quote _fs))
(while (and f (not result))
(set 'result (f arg))
(set 'f (first fs))
(set 'fs (rest fs)))
result)
'_f '_fs)))
(define-macro (conjoin )
(let ((_f (eval (first (args))))
(_fs (eval-args (rest (args)))))
(expand
(lambda (arg , result f fs)
(set 'result true)
(set 'f _f)
(set 'fs (quote _fs))
(while (and f result)
(set 'result (f arg))
(set 'f (first fs))
(set 'fs (rest fs)))
result)
'_f '_fs)))
(define (fold-left f init xs)
(if (empty? xs)
init
(fold-left f (f init (first xs)) (rest xs))))
(define (fold-right f xs init)
(if (empty? xs)
init
(f (first xs) (fold-right f (rest xs) init))))
(define-macro (compose )
(let ((_fns (eval-args (reverse (args)))))
(expand
(lambda-macro ( )
(let ((fns (quote _fns))
(init (eval-args (args))))
(if (empty? fns)
init
(fold-left
(lambda (init f) (f init))
(apply (first fns) init)
(rest fns)))))
'_fns)))
(define (every pred? xs)
(or (empty? xs)
(and (pred? (first xs))
(every pred? (rest xs)))))
(define (some pred? xs)
(and (and (list? xs) (not (empty? xs)))
(or (pred? (first xs))
(some pred? (rest xs)))))
(every integer? '(1 2 3 4)) ;; ==> true
(some integer? '(a b c 4 d)) ;; ==> nil
(filter (disjoin symbol? string?) '(1 a 2 "two" 3))
;; (a "two")
(lambda (x ~y) ....) ;; y is lazy
(lambda-macro (!x y) ...) ;; x is strict
(define (foo x y) ...)
(~foo 1)
(lambda (y , x) (set 'x 1) ... ;; old foo)
(define-macro (qq s-exp)
(while (set 'idx (chop (ref 'uq s-exp)))
(set 'qx (pop s-exp idx))
(push (eval (first (rest qx))) s-exp idx))
s-exp)
;; now use it
(set 'x 'hello)
(qq ( (uq (+ 1 2)) ((uq (+ 3 4)) (uq x)))) => (3 (7 hello))
;; something similar could be done for 'uq@'
(ref? (lambda (s-expr) (or (= 'uq s-expr) (= 'uq@ s-expr)))
s-exp)