-
Notifications
You must be signed in to change notification settings - Fork 33
Expand file tree
/
Copy path8.scrbl
More file actions
148 lines (112 loc) · 3.79 KB
/
8.scrbl
File metadata and controls
148 lines (112 loc) · 3.79 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
#lang scribble/manual
@(require "../defns.rkt")
@title[#:tag "Assignment 8" #:style 'unnumbered]{Assignment 8: Patterns}
@(require (for-label (except-in racket ...)))
@(require "../notes/ev.rkt"
"../notes/utils.rkt")
@bold{Due: @assign-deadline[8]}
@(ev '(require knock-plus))
The goal of this assignment is to extend a compiler with new pattern
matching forms for matching lists, vectors, and predicates.
You are given a file @tt{knock-plus.zip} on ELMS with a starter
compiler similar to the @seclink["Knock"]{Knock} language we studied
in class. You are tasked with:
@itemlist[
@item{implementing the @tt{list} pattern,}
@item{implementing the @tt{vector} pattern, and}
@item{implementing the @tt{?} pattern.}
]
The following files have already been updated for you @bold{and should
not be changed by you}:
@itemlist[ @item{@tt{ast.rkt}}
@item{@tt{parse.rkt}}
@item{@tt{interp.rkt}}
@item{@tt{interp-prim.rkt}}
@item{@tt{compile-op.rkt}}
]
So you will only need to modify:
@itemlist[
@item{@tt{compile.rkt}}
]
to correctly implement the new features. These features are described below.
As a convenience, two new n-ary primitives have been added (and fully
implemented): @racket[list] and @racket[vector]. The @racket[list]
primitive takes any number of arguments and produces a list containing
the arguments as elements; the @racket[vector] primitive does the
same, but constructs a vector.
@ex[
(list)
(list 1 2 3)
(list 1 #t #\c)
(vector)
(vector 1 2 3)
(vector 1 #t #\c)]
These are not directly useful in implementing the patterns above, but
do make it easier to write examples and tests.
@section[#:tag-prefix "a8-" #:style 'unnumbered #:tag "list"]{List patterns}
The @racket[(list _p1 ... _pn)] pattern matches a list of elements. The
pattern matches a list with as many elements as there are patterns
@racket[_p1] through @racket[_pn] and each element must match the
respective pattern.
@ex[
(match (list)
[(list) #t]
[_ #f])
(match (list 1 2 3)
[(list x y z) x])
(match (list (list 1) (list 2))
[(list (list x) (list 2)) x])
]
@section[#:tag-prefix "a8-" #:style 'unnumbered #:tag "vector"]{Vector patterns}
The @racket[(vector _p1 ... _pn)] pattern matches a vector of elements. The
pattern matches a vector with as many elements as there are patterns
@racket[_p1] through @racket[_pn] and each element must match the
respective pattern.
@ex[
(match (vector)
[(vector) #t]
[_ #f])
(match (vector 1 2 3)
[(vector x y z) x])
(match (vector (vector 1) (vector 2))
[(vector (vector x) (vector 2)) x])
]
@section[#:tag-prefix "a8-" #:style 'unnumbered #:tag "vector"]{Predicate patterns}
The @racket[(? _f)] pattern matches any value for which the predicate
@racket[_f] returns a true value (any value other than @racket[#f])
when applied to the value being matched. In Knock+, @racket[_f] must be
the name of a user defined function.
@ex[
(define (is-eight? x) (= x 8))
(define (id x) x)
(match 8
[(? is-eight?) #t]
[_ #f])
(match (vector 1 2 3)
[(and (? id) x) x])
(match 16
[(? is-eight?) #t]
[_ #f])
]
@section[#:tag-prefix "a8-" #:style 'unnumbered]{Representing the syntax of patterns}
The AST of patterns is extended as follows:
@#reader scribble/comment-reader
(racketblock
;; type Pat = ...
;; | (List [Listof Pat])
;; | (Vect [Listof Pat])
;; | (Pred Id)
)
The parser includes a @racket[parse-pattern] function that parses a
single pattern:
@ex[
(parse-pattern 'x)
(parse-pattern '(cons x y))
(parse-pattern '(list x y z))
(parse-pattern '(vector x y z))
(parse-pattern '(? f?))
]
@section[#:tag-prefix "a8-" #:style 'unnumbered]{Submitting}
Submit a zip file containing your work to Gradescope. Use @tt{make
submit.zip} from within the @tt{knock-plus} directory to create a zip
file with the proper structure.