### On Serial Substitution and Not Reading The Manual.

==================================================

; I defined no less than six functions performing serial
; substitution:
;
; (serial-substitute '(-> (A B) (B (A B)) (-> B (A C) (B C)))
;                    '((A abc) (B cde) (C xxx)))
;
; =>
;
; (-> (abc cde) (cde (abc cde)) (-> cde (abc xxx) (cde xxx)))
;
; until I learnt that built in primitive function "expand", in one
; of its polymorphic versions, does exactly that. However, I decided
; to publish my versions, just for archive. The final one is only
; four times slower than built in substitution.

(set 'substitute
(lambda(substitute-a l b)
(if (= l substitute-a)
b
(if (list? l)
(map (lambda(x)(substitute substitute-a x b))
l)
l))))

(set 'serial-substitute1
(lambda(l A)
(let ((result l))
(dolist(i A)
(set 'result (substitute (i 0) result (i 1))))
result)))

(set 'metex
(eval (append '(letex)
(list (map (lambda(x)
(list (first x)
(list 'quote (last x))))
(args)))))

(set 'serial-substitute2
(lambda(l A)
(eval (list 'metex A (list 'quote l)))))

(set 'serial-helper3 (lambda(x)(list (first x)
(list 'quote (last x)))))

(set 'serial-substitute3
(lambda(l A)
(eval (list 'letex (map serial-helper3
A)
(list 'quote l)))))

(set 'ss4 '(metex A 'l))
(set 'serial-substitute4
(lambda(l A)
(eval (expand ss4 'A 'l))))

(set 'serial-substitute5
(lambda(l A)
(letex ((A A)(l l))(metex A 'l))))

(set 'serial-substitute6
(lambda(F s)
(eval (let((vars (map first s)))
(list 'local
vars
'(bind s)
(append '(expand F)
(map quote vars)))))))

(set 'serial-substitute7 expand) ; this is one built in

(set 'serial-substitute8 '(lambda())) ; just to test empty loop

(set 'formula '(-> (A B) (B (A B)) (-> B (A C) (B C))))
(set 'substitution ' ((A abc) (B cde) (C xxx)))

(dolist (s '(serial-substitute1 serial-substitute2 serial-substitute3
serial-substitute4 serial-substitute5 serial-substitute6
serial-substitute7 serial-substitute8))
(println s " time (ms): " (time ((eval s) formula substitution) 100000))
(println s " result:    " ((eval s) formula substitution)))

(exit)

serial-substitute1 time (ms): 10681
serial-substitute1 result:    (-> (abc cde) (cde (abc cde)) (-> cde (abc xxx) (cde xxx)))
serial-substitute2 time (ms): 2084
serial-substitute2 result:    (-> (abc cde) (cde (abc cde)) (-> cde (abc xxx) (cde xxx)))
serial-substitute3 time (ms): 1544
serial-substitute3 result:    (-> (abc cde) (cde (abc cde)) (-> cde (abc xxx) (cde xxx)))
serial-substitute4 time (ms): 2114
serial-substitute4 result:    (-> (abc cde) (cde (abc cde)) (-> cde (abc xxx) (cde xxx)))
serial-substitute5 time (ms): 2134
serial-substitute5 result:    (-> (abc cde) (cde (abc cde)) (-> cde (abc xxx) (cde xxx)))
serial-substitute6 time (ms): 1174
serial-substitute6 result:    (-> (abc cde) (cde (abc cde)) (-> cde (abc xxx) (cde xxx)))
serial-substitute7 time (ms): 386
serial-substitute7 result:    (-> (abc cde) (cde (abc cde)) (-> cde (abc xxx) (cde xxx)))
serial-substitute8 time (ms): 119
serial-substitute8 result:    nil