ICS H21 • UC IRVINE • DAVID G. KAY • FALL 2008
Lab Assignment 4
This assignment is due at the end of lab on Friday, October 24.
Choose a partner for this assignment, someone you haven't worked with already. Starting with this assignment, change your language level to Intermediate Student.
(a) Do exercise 12.2.1 (just adapting the program in Figure 33).
Do the Binary Search Tree (BST) exercises 14.2.3 (inorder traversal of a BST), 14.2.4 (searching a BST), 14.2.5 (inserting into a BST), and 14.2.6.
Then, do exercises 14.3.2, 14.3.3, and 14.3.4 (in which the predefined function max, which returns the largest of its arguments, will be useful). Note that the representation of web pages used in this section is a bit odd, since each linked page is nested within the page that links to it (and you can't, therefore, have two pages that link to each other). It's still a useful vehicle for these exercises, which explore some fundamental operations on trees, and the authors refine this representation later in the book.
After that, do exercises 14.4.1 (do the data definition and just two of the parts), 14.4.2 (this goes through a list containing other lists, following the same general pattern as the exercises in the previous section), 14.4.3, and 14.4.4.
Collect your definitions for all these exercises into one Scheme file, make sure both partners' names are in a comment at the top, and submit it via Checkmate.
(b) Copy the code for the restaurants program to your machine and run it to make sure it works properly in your environment.
Now, reimplement the collection class to store the restaurants in a binary search tree ordered by the restaurants' names. This will involve changing all the definitions in the collection part of the code, but none of the definitions elsewhere.
Your data definition will be as follows:
;; A treenode is either
;; 1. empty
;; 2. (make-treenode rootvalue left right), where rootvalue is a rrant and left
;; and right are treenodes, representing the left subtree and right subtree,
;; and (this is the BST property) where all of the restaurant names in the left
;; subtree are earlier alphabetically than the name of the rootvalue restaurant,
;; all names in the right subtree are greater, and both subtrees are BSTs.
Here are some tips, hints, and simplifications:
—The code you wrote in part (a) should be a useful guide.
—To compare strings alphabetically, use string=?, string>?, or string<?.
—The collection->list function should do an inorder traversal of the tree, so it produces a sorted list.
—Assume that every restaurant in the collection will have a unique name. Under that assumption, there will be no duplications, so that collection-search will always return a one-element collection or an empty collection.
—Deleting items from a BST is very tricky if the item has two children, because you can't leave holes and you need to maintain the BST property. We'll learn the algorithm for this some day, but for now, you can skip it: collection-remove can just return the same collection unchanged.
After completing the task of reimplementing the collection,
add one new feature to the program: c:
Change prices for the dishes served.
When the user types 'c',
the program should ask the user for an amount (positive or negative) representing
a percentage change in price (so that 100 would double a price and -50 would
cut it in half). Then it should apply that price change to the prices for
all the restaurants in the collection. [Here are some hints on how to approach
this. You can think about doing it before reading further. You might approach
this first by writing a rrant-change-price
function that takes a restaurant and a percentage change number, as above,
and returns a restaurant that has all the same information, except that
the price is changed appropriately. Next you might write a function to
apply rrant-change-price
to all the restaurants in the collection. Finally, you can incorporate
these calls into the main program, adding the appropriate command handling
and so on.]
(c) (extra credit; choose any or all, according to the usual rules)
(c.1) Do exercises 12.4.1 and 12.4.2.
(c.2) Try to refine the evaluate function from section 14.4 to handle all-numeric expressions (as before) and also expressions with one variable. You'd start with (define evaluate (lambda (exp var num) ...), which returns the value of exp (with num substituted for each occurrence of var). Refine evaluate further to take a list of variable-value pairs and substitute all the values for their respective variables.
(c.3) Implement "lazy deletion" to effect the removal of nodes from the restaurant BST. Lazy deletion works as follows: The basic idea is that you never really delete anything; you just ignore the nodes that are supposed to be deleted. Each treenode has an additional boolean field called deleted? , which starts out false. When the user asks to delete a node, the deletion function just sets that field to true. (Of course, this means that the traversal routine has to ignore the deleted nodes, the predicate for emptiness has to check more thoroughly, and the routine for adding a node needs to check deleted nodes and, if that's the node being (re-)added, reset the deleted? field to false.) Lazy deletion is more than just a cheap trick to avoid a complicated algorithm; with some kinds of data, it's the best way to do it. In other situations, though, it's terrible. Can you characterize which situations are which? Do you think lazy deletion would be a reasonable choice for a database of restaurants?
(d) Remember that each partner must
complete a partner evaluation form via the Survey tool on eee.uci.edu.
Based in part on ICS H21assignments by David G. Kay from Fall 2001; modified by David G. Kay, Fall 2004–Fall 2008.