(module tl-test mzscheme
(require "../reduction-semantics.ss"
"test-util.ss")
(reset-count)
(define grammar
(language (M (M M)
number)
(E hole
(E M)
(number E))
(X (number any)
(any number))
(Q (Q ...)
variable)
(UN (add1 UN)
zero)))
(define-metafunction f
grammar
[(side-condition (number_1 number_2)
(< (term number_1)
(term number_2)))
x]
[(number 1) y]
[(number_1 2) ,(+ (term number_1) 2)]
[(4 4) q]
[(4 4) r])
(define-metafunction g
grammar
[X x])
(test (term (f (1 17))) 'x)
(test (term (f (11 1))) 'y)
(test (term (f (11 2))) 13)
(test (term (f (4 4))) 'q)
(test (with-handlers ((exn? (λ (x) 'exn-raised))) (term (g (4 4))) 'no-exn)
'exn-raised)
(test (with-handlers ((exn? (λ (x) 'exn-raised))) (term (f mis-match)) 'no-exn)
'exn-raised)
(define-metafunction h
grammar
[(M_1 M_2) ((h M_2) (h M_1))]
[number_1 ,(+ (term number_1) 1)])
(test (term (h ((1 2) 3)))
(term (4 (3 2))))
(define-metafunction h2
grammar
[(Q_1 ...) ((h2 Q_1) ...)]
[variable z])
(test (term (h2 ((x y) a b c)))
(term ((z z) z z z)))
(define-metafunction odd
grammar
[zero #f]
[(add1 UN_1) (even UN_1)])
(define-metafunction even
grammar
[zero #t]
[(add1 UN_1) (odd UN_1)])
(test (term (odd (add1 (add1 (add1 (add1 zero))))))
(term #f))
(let ()
(define-metafunction pRe
(language)
[xxx 1])
(define-metafunction Merge-Exns
(language)
[any_1 any_1])
(test (term (pRe (Merge-Exns xxx)))
1))
(let ()
(define-metafunction f
(language)
[(x) ,(term-let ([var-should-be-lookedup 'y]) (term (f var-should-be-lookedup)))]
[y y]
[var-should-be-lookedup var-should-be-lookedup])
(test (term (f (x))) (term y)))
(let ()
(define-metafunction f
(language)
[(x) (x ,@(term-let ([var-should-be-lookedup 'y]) (term (f var-should-be-lookedup))) x)]
[y (y)]
[var-should-be-lookedup (var-should-be-lookedup)])
(test (term (f (x))) (term (x y x))))
(let ()
(define-metafunction f
(language)
[(any_1 any_2)
case1
(side-condition (not (equal? (term any_1) (term any_2))))
(side-condition (not (equal? (term any_1) 'x)))]
[(any_1 any_2)
case2
(side-condition (not (equal? (term any_1) (term any_2))))]
[(any_1 any_2)
case3])
(test (term (f (q r))) (term case1))
(test (term (f (x y))) (term case2))
(test (term (f (x x))) (term case3)))
(let ()
(define-metafunction zip (language)
[((variable_id ..._1) (number_val ..._1))
((variable_id number_val) ...)])
(test (term (zip ((a b) (1 2)))) (term ((a 1) (b 2)))))
(test (pair? (test-match grammar M '(1 1))) #t)
(test (pair? (test-match grammar M '(1 1 1))) #f)
(test (pair? (test-match grammar
(side-condition (M_1 M_2) (equal? (term M_1) (term M_2)))
'(1 1)))
#t)
(test (pair? (test-match grammar
(side-condition (M_1 M_2) (equal? (term M_1) (term M_2)))
'(1 2)))
#f)
(test (pair? ((test-match grammar M) '(1 1)))
#t)
(define base-grammar
(language
(q 1)
(e (+ e e) number)
(x (variable-except +))))
(define extended-grammar
(extend-language
base-grammar
(e .... (* e e))
(x (variable-except + *))
(r 2)))
(test (pair? (test-match extended-grammar e '(+ 1 1))) #t)
(test (pair? (test-match extended-grammar e '(* 2 2))) #t)
(test (pair? (test-match extended-grammar r '2)) #t)
(test (pair? (test-match extended-grammar q '1)) #t)
(test (pair? (test-match extended-grammar x '*)) #f)
(test (pair? (test-match extended-grammar x '+)) #f)
(test (pair? (test-match extended-grammar e '....)) #f)
(test (regexp-match #rx"[.][.][.][.]" (with-handlers ([exn? exn-message]) (language (e ....))))
'("...."))
(test (apply-reduction-relation
(reduction-relation
grammar
(--> (in-hole E_1 (number_1 number_2))
(in-hole E_1 ,(* (term number_1) (term number_2)))))
'((2 3) (4 5)))
(list '(6 (4 5))))
(test (apply-reduction-relation
(reduction-relation
grammar
(~~> (number_1 number_2)
,(* (term number_1) (term number_2)))
where
[(~~> a b) (--> (in-hole E_1 a) (in-hole E_1 b))])
'((2 3) (4 5)))
(list '(6 (4 5))))
(test (apply-reduction-relation
(reduction-relation
grammar
(==> (number_1 number_2)
,(* (term number_1) (term number_2)))
where
[(~~> a b) (--> (M_1 a) (M_1 b))]
[(==> a b) (~~> (M_1 a) (M_1 b))])
'((1 2) ((2 3) (4 5))))
(list '((1 2) ((2 3) 20))))
(test (apply-reduction-relation
(reduction-relation
grammar
(~~> (number_1 number_2)
,(* (term number_1) (term number_2)))
(==> (number_1 number_2)
,(* (term number_1) (term number_2)))
where
[(~~> a b) (--> (M_1 a) (M_1 b))]
[(==> a b) (--> (a M_1) (b M_1))])
'((2 3) (4 5)))
(list '(6 (4 5))
'((2 3) 20)))
(test (apply-reduction-relation
(reduction-relation
grammar
(--> (M_1 (number_1 number_2))
(M_1 ,(* (term number_1) (term number_2))))
(==> (number_1 number_2)
,(* (term number_1) (term number_2)))
where
[(==> a b) (--> (a M_1) (b M_1))])
'((2 3) (4 5)))
(list '((2 3) 20)
'(6 (4 5))))
(test (apply-reduction-relation/tag-with-names
(reduction-relation
grammar
(--> (number_1 number_2)
,(* (term number_1) (term number_2))
mul))
'(4 5))
(list (list "mul" 20)))
(test (apply-reduction-relation/tag-with-names
(reduction-relation
grammar
(--> (number_1 number_2)
,(* (term number_1) (term number_2))
"mul"))
'(4 5))
(list (list "mul" 20)))
(test (apply-reduction-relation/tag-with-names
(reduction-relation
grammar
(--> (number_1 number_2)
,(* (term number_1) (term number_2))))
'(4 5))
(list (list #f 20)))
(test (apply-reduction-relation/tag-with-names
(reduction-relation
grammar
(==> (number_1 number_2)
,(* (term number_1) (term number_2))
mult)
where
[(==> a b) (--> (M_1 a) (M_1 b))])
'((2 3) (4 5)))
(list (list "mult" '((2 3) 20))))
(test (let ([x 0])
(reduction-relation
(begin (set! x (+ x 1))
(language))
(--> 0 1)
(--> 1 2)
(==> 2 3)
(==> 3 4)
where
[(==> a b) (--> a b)])
x)
1)
(test (let ([lang (language)])
(apply-reduction-relation
(union-reduction-relations
(reduction-relation lang
(--> x a)
(--> x b))
(reduction-relation lang
(--> x c)
(--> x d)))
'x))
(list 'a 'b 'c 'd))
(test (apply-reduction-relation
(reduction-relation
(language)
(--> (number_1 number_2)
number_2
(side-condition (< (term number_1) (term number_2))))
(--> (number_1 number_2)
number_1
(side-condition (< (term number_2) (term number_1)))))
'(1 2))
(list 2))
(parameterize ([current-namespace syn-err-test-namespace])
(eval `(define grammar ,grammar)))
(test-syn-err (reduction-relation
grammar
(~~> (number_1 number_2)
,(* (term number_1) (term number_2)))
where
[(~~> a b) (--> (M a) (M b))]
[(==> a b) (~~> (M a) (M b))])
#rx"no rules")
(test-syn-err (reduction-relation
grammar
(~~> (number_1 number_2)
,(* (term number_1) (term number_2))))
#rx"no --> rules")
(test-syn-err (reduction-relation
grammar
(--> (number_1 number_2)
,(* (term number_1) (term number_2))
mult)
(--> (number_1 number_2)
,(* (term number_1) (term number_2))
mult))
#rx"same name on multiple rules")
(test-syn-err (reduction-relation
grammar
(--> 1 2)
(==> 3 4))
#rx"not defined.*==>")
(test-syn-err (reduction-relation
(language)
(--> 1 2)
(==> 3 4)
where
[(==> a b) (~> a b)])
#rx"not defined.*~>")
(test-syn-err (language (e name)) #rx"name")
(test-syn-err (language (name x)) #rx"name")
(test-syn-err (language (x_y x)) #rx"x_y")
(test (with-handlers ((exn? (λ (x) 'passed)))
(union-reduction-relations
(reduction-relation
grammar
(--> (number_1 number_2)
,(* (term number_1) (term number_2))
mult))
(reduction-relation
grammar
(--> (number_1 number_2)
,(* (term number_1) (term number_2))
mult)))
'failed)
'passed)
(test (with-handlers ((exn? (λ (x) 'passed)))
(union-reduction-relations
(union-reduction-relations
(reduction-relation
grammar
(--> (number_1 number_2)
,(* (term number_1) (term number_2))
mult))
(reduction-relation
grammar
(--> (number_1 number_2)
,(* (term number_1) (term number_2))
mult3)))
(union-reduction-relations
(reduction-relation
grammar
(--> (number_1 number_2)
,(* (term number_1) (term number_2))
mult))
(reduction-relation
grammar
(--> (number_1 number_2)
,(* (term number_1) (term number_2))
mult2))))
'passed)
'passed)
(test (apply-reduction-relation
(compatible-closure
(reduction-relation
grammar
(--> (number_1 number_2)
,(* (term number_1) (term number_2))
mult))
grammar
M)
'((2 3) (4 5)))
(list '((2 3) 20)
'(6 (4 5))))
(test (apply-reduction-relation
(compatible-closure
(reduction-relation
grammar
(--> (number_1 number_2)
,(* (term number_1) (term number_2))
mult))
grammar
M)
'(4 2))
(list '8))
(test (apply-reduction-relation
(context-closure
(context-closure
(reduction-relation grammar (--> 1 2))
grammar
(y hole))
grammar
(x hole))
'(x (y 1)))
(list '(x (y 2))))
(test (apply-reduction-relation
(reduction-relation
grammar
(--> (variable_1 variable_2)
(variable_1 variable_2 x)
mul
(fresh x)))
'(x x1))
(list '(x x1 x2)))
(test (apply-reduction-relation
(reduction-relation
grammar
(~~> number
x
(fresh x))
where
[(~~> a b) (--> (variable_1 variable_2 a) (variable_1 variable_2 b))])
'(x x1 2))
(list '(x x1 x2)))
(test (apply-reduction-relation
(reduction-relation
(language (x variable))
(--> (x_1 ...)
(x ...)
(fresh ((x ...) (x_1 ...)))))
'(x y x1))
(list '(x2 x3 x4)))
(test (apply-reduction-relation
(reduction-relation
(language)
(--> (variable_1 ...)
(x ... variable_1 ...)
(fresh ((x ...) (variable_1 ...) (variable_1 ...)))))
'(x y z))
(list '(x1 y1 z1 x y z)))
(test (apply-reduction-relation
(reduction-relation
(language)
(--> variable_1
(x variable_1)
(fresh (x variable_1))))
'q)
(list '(q1 q)))
(define lc-lang
(language (e (e e ...)
x
v)
(c (v ... c e ...)
hole)
(v (lambda (x ...) e))
(x variable-not-otherwise-mentioned)))
(test (let ([m (test-match lc-lang e (term (lambda (x) x)))])
(and m (length m)))
1)
(test (test-match (extend-language lc-lang
(q a b c))
e
(term (lambda (a) a)))
#f)
(test (let ([m (test-match (extend-language lc-lang
(q a b c))
e
(term (lambda (z) z)))])
(and m (length m)))
1)
(require (lib "list.ss"))
(define-metafunction free-vars
lc-lang
[(e_1 e_2 ...)
,(apply append (term ((free-vars e_1) (free-vars e_2) ...)))]
[x_1 ,(list (term x_1))]
[(lambda (x_1 ...) e_1)
,(foldr remq (term (free-vars e_1)) (term (x_1 ...)))])
(test (term (free-vars (lambda (x) (x y))))
(list 'y))
(test (variable-not-in (term (x y z)) 'x)
(term x1))
(test (variable-not-in (term (y z)) 'x)
(term x))
(test (variable-not-in (term (x x1 x2 x3 x4 x5 x6 x7 x8 x9 x10)) 'x)
(term x11))
(test (variable-not-in (term (x x11)) 'x)
(term x12))
(test (variable-not-in (term (x x1 x2 x3)) 'x1)
(term x4))
(test (variables-not-in (term (x y z)) '(x))
'(x1))
(test (variables-not-in (term (x2 y z)) '(x x x))
'(x x3 x4))
(test ((term-match/single (language)
[(variable_x variable_y)
(cons (term variable_x)
(term variable_y))])
'(x y))
'(x . y))
(test ((term-match/single (language)
[(side-condition (variable_x variable_y)
(eq? (term variable_x) 'x))
(cons (term variable_x)
(term variable_y))])
'(x y))
'(x . y))
(test ((term-match/single (language [x 1])
[(x x)
1])
'(1 1))
1)
(test (let ([x 0])
(cons ((term-match (language)
[(any ... number_1 any ...)
(begin (set! x (+ x 1))
(term number_1))])
'(1 2 3))
x))
'((3 2 1) . 3))
(test ((term-match (language)
[number_1
(term number_1)]
[number_1
(term number_1)])
'1)
'(1 1))
(test (apply-reduction-relation
(reduction-relation
(language (sym variable))
(--> (sym_one sym_!_one sym_!_one sym_!_one)
(sym_one sym_!_one)))
(term (a a b c)))
(list (term (a sym_!_one))))
(printf "tl-test.ss: all ~a tests passed.\n" tests))