Inductively Defined Data Concrete and Abstract syntax Karl Lieberherr CSG 111
Don’t believe the words Concrete syntax may be more abstract than abstract syntax!!! CSG 111
Both Abstract and Concrete Exp ::= Identifier var-exp (id) ::= “(lambda” “(“Identifier”)” Exp”)” lambda-exp (id body) ::= “(“ Exp “(“ Exp “)” “)” app-exp (rator rand) page 49 of EOPL 2: (replace Exp by Expression, capitalize instead of angle) CSG 111
Both Abstract and Concrete Exp ::= Id var-exp (id) ::= “(lambda” “(“ Id ”)” Exp ”)” lambda-exp (id body) ::= “(“ Exp “(“ Exp “)” “)” app-exp (rator rand) (define-datatype Exp Exp? (var-exp (id Id?)) (lambda-exp (id Id?) (body Exp?)) (app-exp (rator Exp?) (rand Exp?))) page 49 of EOPL 2: (Exp by Expression, Id by Identifier, capitalize instead of angle) CSG 111
Represent Id as symbol Exp ::= Id var-exp (id) ::= “(lambda” “(“ Id ”)” Exp ”)” lambda-exp (id body) ::= “(“ Exp “(“ Exp “)” “)” app-exp (rator rand) (define-datatype Exp Exp? (var-exp (id symbol?)) (lambda-exp (id symbol?) (body Exp?)) (app-exp (rator Exp?) (rand Exp?))) page 49 of EOPL 2: (Exp by Expression, Id by Identifier, capitalize instead of angle) CSG 111
cases (define occurs-free? (lambda (var exp) (cases Exp e (var-exp (id) (eqv? id var)) (lambda-exp (id body) and (not (eqv? id var)) (occurs-free? var body))) (app-exp (rator rand) (or … )))))) CSG 111
Exercises for define-datatype Arithmetic expressions ( * (+ 3 5) 7) two arguments only include evaluator Nested containers CSG 111
Variants are also data types Exp ::= Id var-exp (id) ::= “(lambda” “(“ Id ”)” Exp ”)” lambda-exp (id body) ::= “(“ Exp “(“ Exp “)” “)” app-exp (rator rand) (define-datatype Exp Exp? (var-exp (id symbol?)) (lambda-exp (id symbol?) (body Exp?)) (app-exp (rator Exp?) (rand Exp?))) Better way: Exp : VarExp | LambdaExp | AppExp. VarExp = Id. LambdaExp = “(lambda” “(“ <id> Id <body> Exp “)”. AppExp = “(“ <rator> Exp <rand> Exp “)”. Test = <first> LambdaExp <second> AppExp. Each non-terminal defines a data type. CSG 111
Concern analysis Concerns: traversal summing weights (define (check ac) (local (;; Container -> Number ;; the weight of a container ;; effect: the number of capacity violations in a container (define (weight-container ac) (local ([define witems (weight-loi (Container-contents ac))]) (when (> witems (Container-capacity ac)) (set! violations (+ 1 violations))) witems)) ;; (Listof Item) -> Number ;; the weight of a list of items (define (weight-loi l) (foldr + 0 (map weight-item l))) ;; Item -> Number ;; the weight of an item (define (weight-item l) (cond [(Simple? l) (Simple-weight l)] [(Container? l) (weight-container l)])) (define violations 0)) ;; the number of violations detected (weight-container ac) violations)) Concerns: traversal summing weights summing violations CSG 111
Concrete syntax more Abstract than Abstract Syntax: example Exp ::= Identifier var-exp (id) ::= “(lambda” “(“Identifier”)” List(Exp)”)” lambda-exp (id body) ::= “(“ Exp “(“ List(Exp) “)” “)” app-exp (rator rand) page 49 of EOPL 2: (replace Exp by Expression, capitalize instead of angle) CSG 111