COMP6991 RSLogo
Change Log
Assignment Released (2024-03-02)
Copyright By PowCoder代写 加微信 powcoder
https://cgi.cse.unsw.edu.au/~cs6991/forum/
https://cgi.cse.unsw.edu.au/~cs6991/24T1/outline
https://cgi.cse.unsw.edu.au/~cs6991/24T1/blog_posts
https://cgi.cse.unsw.edu.au/~cs6991/24T1/timetable
https://cgi.cse.unsw.edu.au/~cs6991/24T1/lectures
https://cgi.cse.unsw.edu.au/~cs6991/24T1/assignment/01
https://cgi.cse.unsw.edu.au/~cs6991/24T1/lab/05/questions
https://cgi.cse.unsw.edu.au/~cs6991/24T1/workshop/05/questions
COMP6991 23T3 – Assignment 1 Starter VideoCOMP6991 23T3 – Assignment 1 Starter Video
Logo is a programming language derived from lisp and other programming languages. Many older programmers’ first
experience of programming was writing Logo. One of Logo’s main features is its “turtle”: a mechanism for picking up
and putting down a pen, and walking around to draw things.
Your task in this assignment will be to build a Logo interpreter, which writes to a .svg or .png image. You will be
provided with some sample programs, which you are expected to implement correctly. If you pass these tests, and
make a good-faith attempt to accurately implement the described features, you will get the marks for that section.
There will be no surprising “hidden tests”. Should you have a question about the correct functionality of this
program, and the tests don’t specifically answer it; you can assume it’s undefined behaviour which you can
implement however you wish (without purposeful malice).
The goals of this assignment are:
�. To get you to practice designing and structuring a larger Rust program.
�. To focus as much as possible on skills and design patterns that would actually be used when solving modern
programming problems (i.e. writing a pull request, writing re-usable code, etc.)
�. To have fun creating an aesthetic and interesting application, and connecting with the history of programming.
We want to also be explicit about what the goals aren’t:
�. To assess your ability to write large amounts of useless cruft solely for us to mark you on. Where you’re writing
code, we have a reason for it. Where you’re writing text, it’s because we want to genuinely understand your
�. To assess your skills at programming language design. Our Logo dialect has been explicitly designed to be as
simple as possible, and we’ll explain how to parse it (and give some hints on how to structure your interpreter).
Importantly: the big challenge of this assignment is how to design your program. There are no complicated
algorithms (the most complicated thing you may need to do is some recursion, or building a stack… and that’s one of
the last stages), and no “tricks” you’ve got to search for; but it will be difficult to have all the functionality fit “neatly”.
Part of this assignment involves submitting a mark_request.txt file. This gives you an opportunity to talk about both
design excellence, and limitations in your design. If you can identify limitations in your design, we’ll give you some
marks even where we would have otherwise taken them away, since noticing bad design and learning from it is part
of the challenge of the assignment.
An Introduction to the logo language:
A logo program consists of lines of text; which are then split up into tokens (whitespace-separated strings). Lines
starting with // (i.e. two slashes on their own) or empty lines should be ignored as comments.
A token can be one of three things:
A procedure: this is like a function, which can either be part of the interpreter, or implemented within the logo
file. For example, the MAKE procedure sets a variable to a given value. Some procedures take arguments and
some don’t. In later stages of the assignment, we’ll also see procedures which return a value.
A variable: this is a token prefixed by a :, which means you should look up a variable with that name. For
example, :MYVARIABLE might have the value “42”
A value: this is prefixed with a “, and indicates a raw string. All values in logo are stored as strings.
Procedures in Logo always take a fixed number of arguments. For example, MAKE always takes two arguments.
Values in Logo are always strings. Some strings are special though: the exact (i.e. case-sensitive) strings TRUE and
FALSE are interpreted by some operations as booleans. Similarly, If the parse::
into a floating-point number; then the string can be used as a number.
You can choose how you want to handle errors in the language. You can either pre-check for errors in the program
text; or you can just throw an error when you get to an irrecoverable error. The only requirements when you
encounter an error are that you:
Return with an exit code other than 0.
Print a descriptive error message. We suggest that the error should include a relevant line (though since it’s not
always easy to say “what line did the error occur on”, this isn’t a hard requirement).
You must make sure that every token is used. For example, the PENDOWN command which you’ll learn about takes no
arguments. If you were to write PENDOWN 3, that would be an error, since the 3 means nothing.
An Introduction to Unsvg
In this assignment you will use the crate unsvg to generate SVG or PNG image. That crate contains two useful
unsvg::Image which represents an image. It has methods like draw_simple_line which allow you to draw your
image. NOTE: draw_simple_line returns the end coordinates of the line. You do not need to do any maths to
work out where the line ends.
unsvg::get_end_coordinates, which returns where a line drawn from a given point would end.
How your program will work
You will produce a program called rslogo, which always takes four arguments:
a logo program file (these usually end in .lg).
the path to the output SVG or PNG file (must end in .svg or .png)
the height the image should be.
the width the image should be.
We have provided you with starter code. You should use this code as a starting point for your assignment.
You can also run the command 6991 rslogo to play with a sample solution.
Your program should:
�. Read the logo program.
�. Work line by line, parsing then executing the program.
�. Print an error, and then exit with a return code other than 0 if there’s an issue.
�. If there are no issues, write an SVG or PNG using the unsvg crate.
The starter code deals with the basics of command-line arguments and importing the unsvg crate. You must use the
unsvg crate to produce your images.
Design Excellence
Skip this section unless you’re sure you want full marks in the assignment!
https://docs.rs/unsvg/latest/unsvg/
https://cgi.cse.unsw.edu.au/~cs6991/24T1/assignment/01/starter.tar
https://docs.rs/unsvg/latest/unsvg/
Part of the goal of this course is to get you to think about how to write truly great code. To this end, to get 100% in
your “idiomatic design” component, your code requires at least one aspect of “design excellence”: something that
makes your design stand out from the crowd.
If you want to get full marks in this assignment (and it’s OK if you don’t!) then as you go through each part of the
assignment below, think about whether you can do one of these tasks:
Make your errors beautiful. This means:
Your errors should be descriptive, and should include the text of the line that has a problem.
Your errors should provide a hint for what might be wrong, where it’s feasible to do so.
Your errors should be colourful, making it obvious what the text is, and what the issue is. Take inspiration
from the Rust error messages if you can.
You could (but don’t have to) highlight where in the line the issue is, like Rust does.
You may want to consider making use of one of the following diagnostic reporting crates:
annotate-snippets
codespan-reporting
This is “Design Excellence” because it requires structuring your program in a way that you can easily report
errors; and making your program more usable.
Get 80% test coverage for your application. You could use a library like tarpaulin to calculate your test coverage.
Consider approaching this assignment in a Test-Driven Development style if you’re aiming for this design
excellence. This is design excellence because it requires you to think about how to test your program, and to
design a testable program.
Build a parser for rslogo that uses a parser combinator library (e.g. nom, winnow, chumsky).
Create a facility for programmers to add a language extension. The idea is that they should only need to change
like 1 or 2 lines of code, and add a useful command (for example, a REPEAT command that’s like a while loop; or
add trigonometric functions). Additionally, you should document all the public interfaces that are available to a
programmer. You can use #[warn(missing_docs)]) to identify any interfaces that should be documented.
Build your program so it is as close to zero-copy as possible. This is design excellence because it requires you to
think about how to write a performant program, and to think about how to avoid allocating memory.
Write, and create a Pull Request for, a meaningful contribution to the unsvg library (can be documentation, a
new feature, or a bug fix). Before doing this, file an issue so we know what you’re planning on working on, and
create a forum post requesting approval (so we can determine whether your plan is “meaningful” enough to
award marks). This is design excellence because we think that a willingness and knowledge of how to contribute
features to a library is a really important skill for a programmer to have, and generally improves the quality of the
downstream library. You must file the issue before Friday Week 6, so we have time to review it.
(hard) build a transpiler for rslogo that converts rslogo code to another language (e.g. Python, JavaScript, C,
Rust) in order to run it. This isn’t necessarily design excellence, but it’ll force you into some interesting design
challenges that are worth exploring.
We will happily add more design excellence things here, however you need to run them past us first. If you have
an idea, please make a forum post reqeuesting approval!
Note that when deciding if you’ve done “design excellence”, markers won’t be following strict guidelines: a
reasonable, good-faith attempt at one of these tasks is enough. If you’re not sure, ask us!
The Tasks To Complete
Part 1: Turtle Control (20%)
Completing up to this section means you’ll be able to get a maximum of 20% for the Idiomatic Design and Functional Correctness sections
https://crates.io/crates/miette
https://crates.io/crates/ariadne
https://crates.io/crates/chumsky
https://crates.io/crates/annotate-snippets
https://crates.io/crates/codespan-reporting
The first thing we’ll get working in this language is controlling the “turtle”. The turtle is like an invisible pen that can
write on your image. It exists at particular coordinates. It starts “up” (i.e. not drawing), but when you put it “down”,
then moving it should draw a line. The pen also has a colour, which starts as white. The turtle starts facing straight
up, in the center of the screen (note that if the image has odd dimensions, the turtle can be at a floating-point
location).
The turtle can go off the image. The turtle leaving the image should not cause an error. You do not need to do any
bounds-checking, or any special behaviour for the turtle leaving the image.
In this stage, you’ll be required parse the following commands:
FORWARD [numpixels:f32]
BACK [numpixels:f32]
LEFT [numpixels:f32]
RIGHT [numpixels:f32]
SETPENCOLOR [colorcode:f32]
TURN [degrees:f32]
SETHEADING [degrees:f32]
SETX [location:f32]
SETY [location:f32]
PENUP and PENDOWN
As described previously, the turtle can be in two states: “up” or “down”. If the turtle is “up” (which is the state it
starts in), then it does not do any drawing. It can move around without affecting the image. If the turtle is “down”, it
should draw a line wherever it travels.
FORWARD “[numpixels], BACK “[numpixels], LEFT “[numpixels],
RIGHT “[numpixels].
These commands move the turtle. Initially, “forward” means “up the screen”, and “back” means “down the screen”.
Once you implement the turn/set-heading commands, these commands are relative to the direction the turtle is
facing. The argument to this command must be a number. If you are unable to convert the argument to a number,
you should print an error and exit with a non-zero exit code.
If the turtle is “down”, remember that these should also draw a line.
Note that the turtle is able to go off the image. You do not need to do any bounds-checking, or any special behaviour
for the turtle leaving the image. numpixels can also be negative, which means the turtle “reverses” in that direction
(i.e. FORWARD “-10 goes back 10 pixels)
SETPENCOLOR “[colorcode]
The pen starts by drawing white lines. This changes what color the pen draws.
The pen color can be one of 16 options. They are specified in the COLORS array of unsvg. For example, 0 is black and
15 is grey.
SETPENCOLOR “15
SETPENCOLOR “Yeet
… (prints an error about an invalid color)
It should be an error if the number is not an integer.
TURN “[degrees] and SETHEADING “[degrees]
These commands can turn the turtle by a particular integer number of degrees, or set the heading to a particular
direction. The heading 0 is heading up the image, 90 is heading right; 180 is heading south, and 270 is heading left.
This means that a positive argument to TURN will turn the turtle clockwise, and a negative argument will turn it
counter-clockwise.
Note that internally, you shouldn’t normalise the heading. That is, if the turtle is facing 370 degrees, you should
report the turtle as facing 370 degrees, not 10 degrees.
Having anything other than an integer as the degrees here should cause an error.
SETX “[position] and SETY “[position]
These commands set the X and Y position of the turtle respectively. The position can be any floating point. Note that
even if the turtle is “down”, these commands should not draw anything.
Part 2: Variables and Queries (20%)
Completing up to this section means you’ll be able to get a maximum of 40% for the Idiomatic Design and Functional Correctness sections
The MAKE command in Logo is a procedure used to create and assign variables to values within the Logo
programming language. When you use MAKE, you specify a variable name followed by a value. Logo then associates
the variable with the provided value, effectively storing it for later use. This enables programmers to store and
manipulate data, facilitating the creation of more complex algorithms and procedures. For example, MAKE “x “10
would assign the variable x to have the value 10, allowing subsequent commands to reference and manipulate this
value throughout the program’s execution.
Additionally, you will need to implement the ADDASSIGN command. This is the equivalent of += in most programming
languages. It should be given the name of an existing variable, a value to add, and try to add the two together. It
should be an error for the variable to not exist. It should also be an error if either argument is not a number.
Variables have no scope, so once you create them they are available anywhere. Variables can also be overwritten.
While in the sample solution, variables can have any name (like being plain numbers), we won’t be testing this
behaviour. You should ensure that any valid rust variable name is also valid in your implementation; but you don’t
have to validate this.
You can then use a variable anywhere you could use a raw value. This includes using variables as the value in a MAKE
statement . For example, these two programs should be equivalent:
FORWARD “6
MAKE “DISTANCE “3
ADDASSIGN “DISTANCE :DISTANCE
FORWARD :DISTANCE
Additionally, you should support “queries”, which are procedures which “return” a value. They act very similarly to
variables; except they don’t use :s at the start, and they are set automatically by the program. The queries are:
XCOR: return the current x coordinate.
YCOR: return the current y coordinate.
HEADING: return the current heading.
COLOR: return the color of the pen, as an number.
Part 3: IFs, WHILE, [ ] (20%)
Completing up to this section means you’ll be able to get a maximum of 60% for the Idiomatic Design and Functional Correctness sections
One of the fundamental concepts in Logo is conditional execution and looping. To enhance the capabilities of your
Logo interpreter, you will implement two important commands: IF and WHILE. These commands will help users to
create more complex and dynamic drawings and programs.
In this section, you’ll only be required to implement the IF EQ and WHILE EQ commands. In a future section, we will
explore more types of comparisons.
IF EQ Command
The IF EQ command introduces conditional execution in Logo. It allows you to specify two values, and if those two
values are the same (i.e. they are identical strings), a specific block of code will be executed. If they are not the same,
the block of code should not execute.
In our dialect of Logo, this is what the command will look like:
IF EQ
could be raw values, queries, or variables.
contain more IF statements (or WHILEs).
WHILE EQ Command
The WHILE EQ command is identical to IF EQ, except that at the end of the block, you should check the conditions
again. If the conditions are again equal, you should repeat the block. The block should be repeated continuously until
the condition is false.
WHILE EQ Part 4: Implementing Maths and Comparisons using In the world of computer programming and mathematical notation, there are multiple methods to represent and evaluate mathematical expressions. One method used in programming languages like Logo is known as Polish Notation. Polish Notation, also referred to as prefix notation, differs from the more traditional infix notation by placing operators before their operands. In this section, we will delve into the concept of Polish Notation, explore the idea of a stack, and introduce several fundamental mathematical operations in Logo, including GT, LT, EQ, NE, +, -, *, and /. In Logo, to write the equivalent of Rust’s 3 + 4, you should write: + “3 “4. This is kind of like calling +(3, 4), where A more complicated expression in Logo would be EQ * “3 “4 * + “3 “3 “2. Rewriting this in the style above, this The full list of operators in Logo are: EQ NE GT LT AND OR 程序代写 CS代考 加微信: powcoder QQ: 1823890830 Email: powcoder@163.com
a Stack (20%)
Completing up to this section means you’ll be able to get a maximum of 80% for the Idiomatic Design and Functional Correctness sections
the + function adds two numbers together.
is: ==(*(3, 4), *(+(3, 3), 2)). Rewriting it again, it’s 3 * 4 == (3 + 3) * 2, which evaluates to TRUE.
a word, raise an error.
neither a number, a boolean nor a word, raise an error.
a number, raise an error.
number, raise an error.
is not a boolean, raise an error.