28 Also note that the running time of each part will be restricted to a |
28 Also note that the running time of each part will be restricted to a |
29 maximum of 30 seconds on my laptop. |
29 maximum of 30 seconds on my laptop. |
30 |
30 |
31 \DISCLAIMER{} |
31 \DISCLAIMER{} |
32 |
32 |
|
33 \subsection*{Reference Implementation} |
|
34 |
|
35 As usual, this Scala assignment comes with a reference implementation in form of |
|
36 two \texttt{jar}-files. You can download them from KEATS. This allows you to run any |
|
37 test cases on your own computer. For example you can call Scala on the command line with the |
|
38 option \texttt{-cp bf.jar} and then query any function from the |
|
39 \texttt{bf.scala} template file. You have to |
|
40 prefix the calls with \texttt{CW10a} and \texttt{CW10b}, respectively. For example |
|
41 |
|
42 |
|
43 \begin{lstlisting}[language={},xleftmargin=1mm,numbers=none,basicstyle=\ttfamily\small] |
|
44 $ scala -cp bf.jar |
|
45 scala> import CW10a._ |
|
46 scala> run(load_bff("sierpinski.bf")) |
|
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 \end{lstlisting}%$ |
|
80 |
33 |
81 |
34 |
82 |
35 \subsection*{Part 1 (6 Marks)} |
83 \subsection*{Part 1 (6 Marks)} |
36 |
84 |
37 Coming from Java or C++, you might think Scala is a rather esoteric |
85 Coming from Java or C++, you might think Scala is a rather esoteric |
38 programming language. But remember, some serious companies have built |
86 programming language. But remember, some serious companies have built |
39 their business on |
87 their business on |
40 Scala.\footnote{\url{https://en.wikipedia.org/wiki/Scala_(programming_language)\#Companies}} |
88 Scala.\footnote{\url{https://en.wikipedia.org/wiki/Scala_(programming_language)\#Companies}} |
41 And there are far, far more esoteric languages out there. One is |
89 I claim functional programming is not a fad. And there are far, far |
42 called \emph{brainf***}. You are asked in this part to implement an |
90 more esoteric languages out there. One is called \emph{brainf***}. You |
43 interpreter and compiler for this language. |
91 are asked in this part to implement an interpreter for |
|
92 this language. |
44 |
93 |
45 Urban M\"uller developed brainf*** in 1993. A close relative of this |
94 Urban M\"uller developed brainf*** in 1993. A close relative of this |
46 language was already introduced in 1964 by Corado B\"ohm, an Italian |
95 language was already introduced in 1964 by Corado B\"ohm, an Italian |
47 computer pioneer. The main feature of brainf*** is its minimalistic |
96 computer pioneer. The main feature of brainf*** is its minimalistic |
48 set of instructions---just 8 instructions in total and all of which |
97 set of instructions---just 8 instructions in total and all of which |
50 shown to be Turing complete\ldots{}if this doesn't ring any bell with |
99 shown to be Turing complete\ldots{}if this doesn't ring any bell with |
51 you: it roughly means that every algorithm we know can, in principle, |
100 you: it roughly means that every algorithm we know can, in principle, |
52 be implemented in brainf***. It just takes a lot of determination and |
101 be implemented in brainf***. It just takes a lot of determination and |
53 quite a lot of memory resources. Some relatively sophisticated sample |
102 quite a lot of memory resources. Some relatively sophisticated sample |
54 programs in brainf*** are given in the file \texttt{bf.scala}, including |
103 programs in brainf*** are given in the file \texttt{bf.scala}, including |
55 a brainf*** program for the Sierpinski triangle and Mandelbot set.\bigskip |
104 a brainf*** program for the Sierpinski triangle and the Mandelbrot set.\bigskip |
56 |
105 |
57 \noindent |
106 \noindent |
58 As mentioned above, brainf*** has 8 single-character commands, namely |
107 As mentioned above, brainf*** has 8 single-character commands, namely |
59 \texttt{'>'}, \texttt{'<'}, \texttt{'+'}, \texttt{'-'}, \texttt{'.'}, |
108 \texttt{'>'}, \texttt{'<'}, \texttt{'+'}, \texttt{'-'}, \texttt{'.'}, |
60 \texttt{','}, \texttt{'['} and \texttt{']'}. Every other character is |
109 \texttt{','}, \texttt{'['} and \texttt{']'}. Every other character is |
74 repeated until a counter (memory cell) reaches zero. A typical |
123 repeated until a counter (memory cell) reaches zero. A typical |
75 program in brainf*** looks as follows: |
124 program in brainf*** looks as follows: |
76 |
125 |
77 \begin{center} |
126 \begin{center} |
78 \begin{verbatim} |
127 \begin{verbatim} |
79 ++++++++[>++++[>++>+++>+++>+<<<<-]>+>+>->>+[<]<-]>>.>---.+++++++ |
128 ++++++++[>++++[>++>+++>+++>+<<<<-]>+>+>->>+[<]<-]>>.>---.++ |
80 ..+++.>>.<-.<.+++.------.--------.>>+.>++. |
129 +++++..+++.>>.<-.<.+++.------.--------.>>+.>++. |
81 \end{verbatim} |
130 \end{verbatim} |
82 \end{center} |
131 \end{center} |
83 |
132 |
84 \noindent |
133 \noindent |
85 This one prints out Hello World\ldots{}obviously. |
134 This one prints out Hello World\ldots{}obviously ;o) |
86 |
135 |
87 \subsubsection*{Tasks (file bf.scala)} |
136 \subsubsection*{Tasks (file bf.scala)} |
88 |
137 |
89 \begin{itemize} |
138 \begin{itemize} |
90 \item[(1)] Write a function that takes a file name as argument and |
139 \item[(1)] Write a function that takes a file name as an argument |
91 and requests the corresponding file from disk. It returns the |
140 and requests the corresponding file from disk. It returns the |
92 content of the file as a String. If the file does not exists, |
141 content of the file as a String. If the file does not exists, |
93 the function should return the empty string.\\ |
142 the function should return the empty string.\\ |
94 \mbox{}\hfill[1 Mark] |
143 \mbox{}\hfill[1 Mark] |
95 |
144 |
180 \texttt{--[..[[-]+>[.]]-->,++\barbelow{\;\phantom{+}}} |
229 \texttt{--[..[[-]+>[.]]-->,++\barbelow{\;\phantom{+}}} |
181 \end{center} |
230 \end{center} |
182 \hfill[2 Marks] |
231 \hfill[2 Marks] |
183 |
232 |
184 |
233 |
185 \item[(4)] Write a recursive function \texttt{run} that executes a |
234 \item[(4)] Write a recursive function \texttt{compute} that runs a |
186 brainf*** program. It takes a program, a program counter, a memory |
235 brainf*** program. It takes a program, a program counter, a memory |
187 pointer and a memory as arguments. If the program counter is outside |
236 pointer and a memory as arguments. If the program counter is outside |
188 the program string, the execution stops and \texttt{run} returns the |
237 the program string, the execution stops and \texttt{compute} returns the |
189 memory. If the program counter is inside the string, it reads the |
238 memory. If the program counter is inside the string, it reads the |
190 corresponding character and updates the program counter \texttt{pc}, |
239 corresponding character and updates the program counter \texttt{pc}, |
191 memory pointer \texttt{mp} and memory \texttt{mem} according to the |
240 memory pointer \texttt{mp} and memory \texttt{mem} according to the |
192 rules shown in Figure~\ref{comms}. It then calls recursively |
241 rules shown in Figure~\ref{comms}. It then calls recursively |
193 \texttt{run} with the updated data. The most convenient way to |
242 \texttt{compute} with the updated data. The most convenient way to |
194 implement the rules in \texttt{run} is to use pattern-matching |
243 implement the brainf**k rules in Scala is to use pattern-matching |
195 and calculating a triple consisting of the new \texttt{pc}, |
244 and to calculate a triple consisting of the updated \texttt{pc}, |
196 \texttt{mp} and \texttt{mem}. |
245 \texttt{mp} and \texttt{mem}. |
197 |
246 |
198 Write another function \texttt{start} that calls \texttt{run} with a |
247 Write another function \texttt{run} that calls \texttt{compute} with a |
199 given brainfu** program and memory, and the program counter and memory pointer |
248 given brainfu** program and memory, and the program counter and memory pointer |
200 set to~$0$. Like \texttt{run} it returns the memory after the execution |
249 set to~$0$. Like \texttt{compute}, it returns the memory after the execution |
201 of the program finishes. You can test your brainf**k interpreter with the |
250 of the program finishes. You can test your brainf**k interpreter with the |
202 Sierpinski triangle or the Hello world programs (they seem to be particularly |
251 Sierpinski triangle or the Hello world programs (they seem to be particularly |
203 useful for debugging purposes), or have a look at |
252 useful for debugging purposes), or have a look at |
204 |
253 |
205 \begin{center} |
254 \begin{center} |
206 \url{https://esolangs.org/wiki/Brainfuck} |
255 \url{https://esolangs.org/wiki/Brainfuck} |
207 \end{center}\hfill[2 Marks] |
256 \end{center}\hfill[2 Marks] |
208 |
257 |
209 \begin{figure}[p] |
258 \begin{figure}[p] |
210 \begin{center} |
259 \begin{center} |
211 \begin{tabular}{|@{}p{0.8cm}|l|} |
260 \begin{tabular}{|@{\hspace{0.5mm}}p{0.8cm}|l|} |
212 \hline |
261 \hline |
213 \hfill\texttt{'>'} & \begin{tabular}[t]{@{}l@{\hspace{2mm}}l@{}} |
262 \hfill\texttt{'>'} & \begin{tabular}[t]{@{}l@{\hspace{2mm}}l@{}} |
214 $\bullet$ & $\texttt{pc} + 1$\\ |
263 $\bullet$ & $\texttt{pc} + 1$\\ |
215 $\bullet$ & $\texttt{mp} + 1$\\ |
264 $\bullet$ & $\texttt{mp} + 1$\\ |
216 $\bullet$ & \texttt{mem} unchanged |
265 $\bullet$ & \texttt{mem} unchanged |