Graphic by Keith Ohlfs
CS111, Wellesley College, Spring 2000

Problem Set 9

Due: Friday, May 5, by 4:00 p.m.

[CS111 Home Page] [Syllabus] [Students] [Lecture Notes] [Assignments] [Programs] [Documentation] [Software Installation] [FAQ] [CS Dept.] [CWIS]


Reading Assignment:

About this Problem Set

The purpose of this problem set is to give you experience with lists of lists (Task 1) and with graphical user interfaces (Task 2). In Task 2, you will also get experience writing a complete program almost entirely from scratch.

How to turn in this Problem Set

Homework Problems :

Turn in only one package of hardcopy materials. Staple your files together with the cover page, and submit your hardcopy package by placing it in the box outside of Stanzi's office (SCI E106).

Reminders

  1. Pay careful attention to upper and lower case letters in the filenames.
  2. Once you have used Fetch to upload a file to the cs111 server, you should be sure to doublecheck that the file was actually uploaded. You can do this in Fetch by verifying that the file is now listed in your directory. Not only should you check that the file is listed, but you should check that it does not have a size of 0K. If the file isn't listed or if the size for the document is 0K, this means that there was an error in transferring it via Fetch and you must re-upload the document. When transferring a folder, you should check that its contents have been uploaded correctly. That is, you should be sure to check that every single file that you wish to submit has been uploaded correctly. Often times, although not always, you will see a message "Connection Failed" when there is an error in transferring your files.
  3. If you have trouble uploading files, it may be because you have reached the limits of your Nike file system quota. You will get an error message informing you that this is the problem. In this case, you need to delete some of your old files, either from your home directory or your drop folders (which are also counted toward your quota). To delete a file in Fetch, just drag it to the Trash.


Task 1: Making Change

Lists of lists are useful data structures for holding lists of possibilities. For example, as seen in lecture and lab, we can use them to hold the list of all permutations and subsequences of a list of numbers.

In this problem, we will use lists of lists to represent all the possible ways of making change for a given amount of money using an unlimited number of coins from a given list of denominations. You may assume that the amount of money is a non-negative integer, and that the list of coin denominations is a list of distinct positive integers ordered in decreasing order. When making change for the given amount, you may use any number of "copies" of the coins in the denomination list.

In the resulting list of lists, each element (which we shall call a change list) should be a list of coin values sorted in order of decreasing value whose sum is the given amount of money. These change lists should be ordered in reverse lexicographic order (i.e., reverse dictionary order). That is, change lists with a larger first coin come before change lists with a smaller first coin. If two change lists have the same first coin, the one with the largest second coin goes first. And so on.

Here are a few simple examples:

Amount of money

Denominations

Ways to Make Change

5

[5,1]

[[5],
 [1,1,1,1,1]
 ]

1 nickel or 5 pennies

16

[10,5,1]

[[10, 5, 1],
 [10, 1, 1, 1, 1, 1, 1],
 [5, 5, 5, 1],
 [5, 5, 1, 1, 1, 1, 1, 1],
 [5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1]
 ]
16
[10,5]
[]
21
[10,5,1]
[[10, 10, 1],
 [10, 5, 5, 1],
 [10, 5, 1, 1, 1, 1, 1, 1],
 [10, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [5, 5, 5, 5, 1],
 [5, 5, 5, 1, 1, 1, 1, 1, 1],
 [5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1]

]

Your goal is to formulate a strategy that will list all the possible ways to make change for a given amount of money with a list of possible denominations provided in descending order of value. To do this, you will flesh out the makeChange() method in the ChangeMaker.java file within the ChangeMaker folder of ps9_programs. The contract for the method is as follows:

public static IntListList makeChange (int amount, IntList coins)
Assume that amount is a non-negative integer and that coins is a list of distinct positive integers in descending order. Returns a list of all possible change lists, where a change list is a list of denominations taken from coins (potentially with duplicates) whose sum is amount. The denominations in a change list should be in descending order. The change lists themselves should be ordered in reverse lexicographic order.

Notes

Correct Test Case Answers

----------------------------------------------------
There are 2 ways to make change for 5 cents using [10, 5, 1]:
[[5],
 [1, 1, 1, 1, 1]
 ]
----------------------------------------------------
There are 6 ways to make change for 16 cents using [10, 5, 1]:
[[10, 5, 1],
 [10, 1, 1, 1, 1, 1, 1],
 [5, 5, 5, 1],
 [5, 5, 1, 1, 1, 1, 1, 1],
 [5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1]
 ]
----------------------------------------------------
There are 9 ways to make change for 21 cents using [25, 10, 5, 1]:
[[10, 10, 1],
 [10, 5, 5, 1],
 [10, 5, 1, 1, 1, 1, 1, 1],
 [10, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [5, 5, 5, 5, 1],
 [5, 5, 5, 1, 1, 1, 1, 1, 1],
 [5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1]
 ]
----------------------------------------------------
There are 13 ways to make change for 26 cents using [25, 10, 5, 1]:
[[25, 1],
 [10, 10, 5, 1],
 [10, 10, 1, 1, 1, 1, 1, 1],
 [10, 5, 5, 5, 1],
 [10, 5, 5, 1, 1, 1, 1, 1, 1],
 [10, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [5, 5, 5, 5, 5, 1],
 [5, 5, 5, 5, 1, 1, 1, 1, 1, 1],
 [5, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1]
 ]
----------------------------------------------------
There are 60 ways to make change for 56 cents using [25, 10, 5, 1]:
[[25, 25, 5, 1],
 [25, 25, 1, 1, 1, 1, 1, 1],
 [25, 10, 10, 10, 1],
 [25, 10, 10, 5, 5, 1],
 [25, 10, 10, 5, 1, 1, 1, 1, 1, 1],
 [25, 10, 10, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [25, 10, 5, 5, 5, 5, 1],
 [25, 10, 5, 5, 5, 1, 1, 1, 1, 1, 1],
 [25, 10, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [25, 10, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [25, 10, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [25, 5, 5, 5, 5, 5, 5, 1],
 [25, 5, 5, 5, 5, 5, 1, 1, 1, 1, 1, 1],
 [25, 5, 5, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [25, 5, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [25, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [25, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [25, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 10, 10, 10, 10, 5, 1],
 [10, 10, 10, 10, 10, 1, 1, 1, 1, 1, 1],
 [10, 10, 10, 10, 5, 5, 5, 1],
 [10, 10, 10, 10, 5, 5, 1, 1, 1, 1, 1, 1],
 [10, 10, 10, 10, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 10, 10, 10, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 10, 10, 5, 5, 5, 5, 5, 1],
 [10, 10, 10, 5, 5, 5, 5, 1, 1, 1, 1, 1, 1],
 [10, 10, 10, 5, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 10, 10, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 10, 10, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 10, 10, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 10, 5, 5, 5, 5, 5, 5, 5, 1],
 [10, 10, 5, 5, 5, 5, 5, 5, 1, 1, 1, 1, 1, 1],
 [10, 10, 5, 5, 5, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 10, 5, 5, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 10, 5, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 10, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 10, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 10, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 5, 5, 5, 5, 5, 5, 5, 5, 5, 1],
 [10, 5, 5, 5, 5, 5, 5, 5, 5, 1, 1, 1, 1, 1, 1],
 [10, 5, 5, 5, 5, 5, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 5, 5, 5, 5, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 5, 5, 5, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 5, 5, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 5, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [10, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 1],
 [5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 1, 1, 1, 1, 1, 1],
 [5, 5, 5, 5, 5, 5, 5, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [5, 5, 5, 5, 5, 5, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [5, 5, 5, 5, 5, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [5, 5, 5, 5, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [5, 5, 5, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [5, 5, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [5, 5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [5, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
 [1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1]
 ]
----------------------------------------------------
There are 2 ways to make change for 15 cents using [10, 5]:
[[10, 5],
 [5, 5, 5]
 ]
----------------------------------------------------
There are 0 ways to make change for 16 cents using [10, 5]:
[ ]
----------------------------------------------------


Task 2: Color Guessing

The "Guess The Color" Game

This problem involves a simple game in which a player guesses the red, green, and blue components of a randomly chosen color. The game is played using an applet whose initial appearance is as follows:

The applet has the following parts:

Pressing the New Game button starts a new game. Starting a new game zeroes out the three text fields and displays a randomly chosen color on the canvas, which we will refer to as the secret color. It also displays the message "Press Guess to make a guess; Hint for a hint." in the message line.

The goal of the game is to guess the RGB (Red/Green/Blue) components of the secret color. Recall that RGB components are numbers between 0 and 255. A guess is entered by typing numbers into the three text fields and pressing the Guess button. Here is the result of a first guess:

Whenever a guess is made, the canvas is changed to show a rectangular "ring" with the guessed color. In this example, the guessed color is a light purple while the secret color is a darker purple. The area outside the ring and the the "hole" inside the ring both show the secret color. Showing secret color both outside and inside makes it easier to compare the guessed color to the secret one. The "thickness" of the ring segments are one-fifth the size of the canvas in each dimension.

Since it is surprisingly difficult to get the colors to match, a "hint" option is provided. Pressing the Hint button indicates for each color component whether it needs to be made larger, smaller, or kept the same. (In this respect, the game is like the classical game of Hi/Lo, except that it is played with three secret numbers at once.) As with guesses, hints are numbered. For example, pressing the Hint button in our running game yields.

Play continues with the player making more guesses and optionally choosing to see hints. Below are some snapshots from a running game.

As indicated by the last of the above pictures, the differences between the guessed color and the secret color can be so small as to be almost undetectable by the human eye. Human vision is not the only problem; some computer screens/and or color mapping software don't accurately display all subtle color differences. In this case, the hint information is extremely helpful for getting the "correct" answer!

When the correct RGB value has been guessed, the message line displays a message indicating this fact, along with the number of guesses and hints that were used in the process.

Using binary search in conjunction with hints, it is possible to guess the components of any secret color in no more than 8 guesses. But you can achieve this result even if you don't see the secret color! With enough practice, you can do better than 8 guesses if you use the feedback provided by the color in the canvas. (If there is sufficient interest, we can hold a contest to see who can reliably guess colors with the fewest number of guesses.)

In some cases, a player may just want to surrender and be shown the answer. To do this, the player presses the I Give Up! button. Here is the result of doing this in a different game:

The Guess, Hint, and I Give Up buttons only work when there is a game in progress. Pressing these buttons when one game has finished but a new one has not yet begun (by pressing the New Game button) results in the following error message in the message line:

 

Your Task

Your task is to implement the "Guess the Color" game described above. You will be writing the program almost entirely from scratch. All you are given is a rather empty skeleton file GuessTheColor.java, which you must flesh out to have the appearance and behavior of the applet described above. Here are some notes/hints on how to proceed:

Extra Credit

The Guess the Color game can be improved in many ways. Below are some improvements you might want to implement for extra credit. Feel free to extend the game in other ways you find interesting.

To submit extra credit, create a copy of the GuessTheColor folder named ExtraCredit that contains all of your modified code. For your softcopy, upload your ExtraCredit folder to the ps9 drop folder. For your hardcopy submission, submit (1) a description of what modificiations you made to the program and (2) your final version of GuessTheColor.java.