;; Types (define make-type (lambda (name) name)) (define typed-value-packer (lambda (type) (lambda (value) (cons type value)))) (define typed-value-unpacker (lambda (type) (lambda (value) (if (equal? type (car value)) (cdr value) (error "type mismatch"))))) (define movie-type (make-type 'movie)) (define pack-movie (typed-value-packer movie-type)) (define unpack-movie (typed-value-unpacker movie-type)) (define make-movie (lambda (title director year actors) (pack-movie (list title director year actors)))) (define movie-title (lambda (movie) (car (unpack-movie movie)))) (define movie-director (lambda (movie) (car (cdr (unpack-movie movie))))) (define movie-year (lambda (movie) (car (cdr (cdr (unpack-movie movie)))))) (define movie-actors (lambda (movie) (cadddr (unpack-movie movie)))) (define director-type (make-type 'director)) (define pack-director (typed-value-packer director-type)) (define unpack-director (typed-value-unpacker director-type)) (define make-director (lambda (name) (pack-director name))) (define director-name (lambda (director) (unpack-director director))) (define year-type (make-type 'year)) (define pack-year (typed-value-packer year-type)) (define unpack-year (typed-value-unpacker year-type)) (define make-year (lambda (number) (pack-year number))) (define year-number (lambda (year) (unpack-year year))) (define actor-type (make-type 'actor)) (define pack-actor (typed-value-packer actor-type)) (define unpack-actor (typed-value-unpacker actor-type)) (define make-actor (lambda (name) (pack-actor name))) (define actor-name (lambda (actor) (unpack-actor actor))) (define title-type (make-type 'title)) (define pack-title (typed-value-packer title-type)) (define unpack-title (typed-value-unpacker title-type)) (define make-title (lambda (name) (pack-title name))) (define title-name (lambda (title) (unpack-title title))) (define construct-movie (lambda (title-name director-name year-number actor-names) (make-movie (make-title title-name) (make-director director-name) (make-year year-number) (map make-actor actor-names)))) (define our-movie-database ; longer version than in the text (list (construct-movie '(amarcord) '(federico fellini) 1974 '((magali noel) (bruno zanin) (pupella maggio) (armando drancia))) (construct-movie '(the big easy) '(jim mcbride) 1987 '((dennis quaid) (ellen barkin) (ned beatty) (lisa jane persky) (john goodman) (charles ludlam))) (construct-movie '(boyz n the hood) '(john singleton) 1991 '((cuba gooding jr.) (ice cube) (larry fishburne) (tyra ferrell) (morris chestnut))) (construct-movie '(dead again) '(kenneth branagh) 1991 '((kenneth branagh) (emma thompson) (andy garcia) (derek jacobi) (hanna schygulla))) (construct-movie '(the godfather) '(francis ford coppola) 1972 '((marlon brando) (al pacino) (james caan) (robert duvall) (diane keaton))) (construct-movie '(an american in paris) '(vincente minnelli) 1952 '((gene kelley) (leslie caron) (oscar levant) (nina foch) (george guetary))) (construct-movie '(casablanca) '(michael curtiz) 1942 '((humphrey bogart) (ingrid bergman) (paul henreid) (claude rains) (sydney greenstreet) (peter lorre) (s z sakall) (conrad veidt) (dooley wilson))) (construct-movie '(citizen kane) '(orson welles) 1941 '((orson welles) (joseph cotten) (dorothy comingore) (ray collins) (george coulouris) (agnes moorehead) (ruth warrick))) (construct-movie '(gone with the wind) '(victor fleming) 1939 '((clark gable) (vivien leigh) (leslie howard) (olivia de havilland) (hattie mcdaniel) (butterfly mcqueen))) (construct-movie '(lawrence of arabia) '(david lean) 1962 '((peter otoole) (alec guinness) (anthony quinn) (jack hawkins) (jose ferrer) (omar sharif) (anthony quayle) (claude rains) (arthur kennedy) (donald wolfit))) (construct-movie '(the manchurian candidate) '(john frankenheimer) 1962 '((frank sinatra) (laurence harvey) (janet leigh) (angela lansbury) (henry silva) (james gregory) (leslie parrish) (john mcgiver) (khigh dhiegh) (james edwards))) (construct-movie '(metropolis) '(fritz lang) 1926 '((alfred abel) (gustay frohlich) (brigitte helm) (rudolf kleinrogge) (heinrich george))) (construct-movie '(othello) '(orson welles) 1952 '((orson welles) (michael mac liammoir) (robert coote) (suzanne cloutier) (faye compton) (doris dowling) (michael laurence))) (construct-movie '(spartacus) '(stanley kubrick) 1960 '((kirk douglas) (laurence olivier) (jean simmons) (charles laughton) (peter ustinov) (john gavin) (tony curtis) (woody strode))) (construct-movie '(a star is born) '(george cuckor) 1954 '((judy garland) (james mason) (jack carson) (tommy noonan) (charles bickford))) (construct-movie '(after the rehearsal) '(ingmar bergman) 1984 '((erland josephson) (ingrid thulin) (lena olin) (nadja palmstjerna-weiss))) (construct-movie '(amadeus) '(milos forman) 1984 '((f murray abraham) (tom hulce) (elizabeth berridge) (simon callow) (roy dotrice) (christine ebersole) (jeffrey jones))) (construct-movie '(blood simple) '(joel coen) 1985 '((john getz) (frances mcdormand) (dan hedaya) (m emmet walsh) (samm-art williams))) (construct-movie '(chinatown) '(roman polanski) 1974 '((jack nicholson) (faye dunaway) (john huston) (perry lopez) (john hillerman) (darrell zwerling) (diane ladd) (roman polanski))) (construct-movie '(the cotton club) '(francis ford coppola) 1984 '((richard gere) (gregory hines) (diane lane) (lonette mckee) (bob hoskins) (james remar) (fred gwynne))) (construct-movie '(the crying game) '(neil jordan) 1992 '((stephen rea) (jaye davidson) (forest whitaker) (miranda richardson) (adrian dunbar) (breffini mckenna) (joe savino))) (construct-movie '(the day of the jackal) '(fred zinnemann) 1973 '((edward fox) (terence alexander) (michel auclair) (alan badel) (tony britton) (denis carey) (olga georges-picot) (cyril cusack))) (construct-movie '(diva) '(jean-jacques beineix) 1981 '((wilhelmenia wiggins fernandez) (frederic andrei) (richard bohringer) (thay an luu) (jacques fabbri) (chantal deruaz))) (construct-movie '(the dresser) '(peter yates) 1984 '((albert finney) (tom courtenay) (edward fox) (zena walker))) (construct-movie '(el norte) '(gregory nava) 1983 '((zaide silvia gutierrez) (david villalpando) (ernesto gomez cruz) (alicia del lago) (trinidad silva))) (construct-movie '(the exorcist) '(william friedkin) 1973 '((ellen burstyn) (linda blair) (jason miller) (max von sydow) (kitty winn) (lee j cobb))) (construct-movie '(a fish called wanda) '(michael chrichton) 1988 '((john cleese) (jamie lee curtis) (kevin kline) (michael palin) (maria aitken) (tom georgeson) (patricia hayes))) (construct-movie '(flirting) '(john duigan) 1992 '((noah taylor) (thandie newton) (nicole kidman) (bartholomew rose) (felix nobis) (josh picker) (kiri paramore))) (construct-movie '(gates of heaven) '(errol morris) 1978 '()) (construct-movie '(house of games) '(david mamet) 1987 '((lindsay crouse) (joe mantegna) (mike nussman) (lilia skala) (j t walsh) (jack wallace))) (construct-movie '(iceman) '(fred schepisi) 1984 '((timothy hutton) (john lone) (lindsay crouse))) (construct-movie '(jaws) '(steven spielberg) 1975 '((roy scheider) (robert shaw) (richard dreyfuss) (lorraine gary) (murray hamilton))) (construct-movie '(johnny got his gun) '(dalton trumbo) 1971 '((timothy bottoms) (kathy fields) (jason robards) (diane varsi) (donald sutherland) (eduard franz))) (construct-movie '(local hero) '(bill forsyth) 1983 '((burt lancaster) (peter reigert) (peter capaldi) (fulton mckay) (denis lawson))) (construct-movie '(malcolm x) '(spike lee) 1992 '((denzel washington) (angela basset) (albert hall) (al freeman jr) (delroy lindo) (spike lee))))) ; (define display-actor-in-movie? ; (lambda (firstname lastname movie) ; (if (actor-in-movie? (list firstname lastname) movie) ; (display "Yes, indeed.") ; (display "No, that's not the case")))) ; ;(define actor-in-movie? ; (lambda (actor movie) ; (let ((movies (movies-with-title-name movie))) ; (if (null? movies) ; #f ; (member? actor (map actor-name (movie-actors (car movies)))))))) (define filter (lambda (predicate list) (cond ((null? list) '()) ((predicate (car list)) (cons (car list) (filter predicate (cdr list)))) (else (filter predicate (cdr list)))))) (define query-loop (lambda () (let ((question (read))) (if (exit? question) (display '(see you later)) (begin (answer-by-pattern question patterns+actions) (newline) (query-loop)))))) (define answer-by-pattern (lambda (question p/as) (if (null? p/as) (display '(I did not understand your question)) (if (matches? (pattern (car p/as)) question) (let ((subs (substitutions-in-to-match (pattern (car p/as)) question))) (let ((result ((action (car p/as)) subs))) (if (null? result) (display "I don't know") (display result)))) (answer-by-pattern question (cdr p/as)))))) (define exit? (lambda (question) (member? question '((bye) (quit) (exit) (goodbye) (au revoir))))) (define member? (lambda (element list) (cond ((null? list) #f) ((equal? element (car list)) #t) (else (member? element (cdr list)))))) (define movies-with-title-name (lambda (name) (filter (lambda (movie) (equal? name (title-name (movie-title movie)))) our-movie-database))) (define pattern/action-type (make-type 'pattern/action)) (define pack-pattern/action (typed-value-packer pattern/action-type)) (define unpack-pattern/action (typed-value-unpacker pattern/action-type)) (define make-pattern/action (lambda (pattern action) (pack-pattern/action (cons pattern action)))) (define display-directors-of (lambda (title) (display (director-name (movie-director (car (movies-with-title-name title))))))) (define patterns+actions (list (make-pattern/action '(who is the director of ...) display-directors-of))) (define pattern (lambda (p/a) (car (unpack-pattern/action p/a)))) (define action (lambda (p/a) (cdr (unpack-pattern/action p/a)))) (define substitutions-in-to-match (lambda (pattern question) (cond ((equal? (car pattern) (car question)) (substitutions-in-to-match (cdr pattern) (cdr question))) ((equal? (car pattern) '...) question)))) (define matches? (lambda (pattern question) (cond ((null? pattern) (if (null? question) #t #f)) ((null? question) #f) ;; pattern and question non-null? ((equal? '... (car pattern)) #t) ((equal? (car question) (car pattern)) (matches? (cdr pattern) (cdr question))) (else #f))))