You may work with one partner on this assignment. If you work with a partner, put your name and the name of your partner in the list of authors at the top of your program. Only one partner needs to run handin21 to submit the files for the group. Both partners will receive the same grade.
Run update21, if you haven't already, to create the cs21/labs/08 directory. Then cd into your cs21/labs/08 directory and create the python programs for lab 8 in this directory (handin21 looks for your lab 8 assignments in your cs21/labs/08 directory):
$ update21 $ cd cs21/labs/08 $ vi lingo.py
For this assignment, you will write a program that implements the TV game show Lingo. The focus of this assignment is for you to practice using top-down design to construct your solution incrementally.
Lingo is a turn-based guessing game. The computer selects a random word and the player tries to guess the word. Each guess must also be a valid word of the same length (this is what makes the game interesting and hard). After a guess is made, the computer provides status information about how close (or how far) the player is to arriving at the solution. The status information includes which letters are correct, but in the wrong position, and which letters are correct, and in the right position.
To make things concrete, let's use an example where the computer is selecting a five-letter word. Normally, as a player of the game, you would not know what the computer had chosen. However, let's make things easier and peek at the computer's choice: guava.
It's time for you to begin guessing the word. Your initial guess is:
spray. Notice that there is only one letter that you guessed
that's also in the target word (the letter a). Rather than
indicate the number of letters you have correct, the status message
will specify which letters are exactly correct and which are in the
sequence, but in the wrong place. You'll do this by UPPER-CASING the
exact matches, leaving the 'inexact' matches alone, and replacing the
wrong letters with dashes. So, in this case, where the letter
a of your guess spray is an 'inexact' match, you'd
receive the status message:
---a-
Clearly you don't know the word yet, so you make another guess:
arrow. Again, the only correct letter is the a, and
now it's in a different wrong place. So, the status you would receive
is:
a----
Your next guess is again. This time the guessed word has two a's, as does the secret word. The first guessed a is in the wrong position and will appear as lower case, but the second guessed a is in the correct position (the third character) and should show up as an upper case guess in the status. There is also a correctly guessed g but it is in the wrong position and will appear as lower case. Since neither the i nor the n appear in the target word, the status of this guess is the following: agA--
Your next guess is games. While it's true that you know there
are no s's in the solution (from your guess of spray
earlier), you're trying to see if some of these other letters are
present (the m and e) and you're still
trying to figure out where the other a goes. The status message
now shows that you have the g in the right position and the a
is still in the wrong position:
Ga---
Here is this example as it may appear in a game (see the Sample Output section below for other examples of a working solution):
Enter a 5 letter word: spray - - - a - Enter a 5 letter word: arrow a - - - - Enter a 5 letter word: again a g A - - Enter a 5 letter word: games G a - - - Enter a 5 letter word: curve - U - V - Enter a 5 letter word: suave - U A V - Enter a 5 letter word: guava You won in 7 turns!
if word in wordList: ...
>>> word = "apple" >>> word 'apple' >>> charList = list(word) >>> charList ['a', 'p', 'p', 'l', 'e'] >>> rejoined = ''.join(charList) >>> rejoined 'apple'
You may want to first get the entire flow of control correct, with incorrect status updates (perhaps ignoring double characters in guessed and target word, and ignoring the correct position part) , and then go back and work on getting the status update part correct.
We suggest that you store the secret word and the guessed word as strings. Then to produce the status information, create list versions of these words that can be modified. You can use the list version of the guessed word to hold the status information. First search for exact matches. When an exact match is found, change the letter in the guessed word to upper case and hide the letter in the secret word by changing it to some other character, such as '.' (you don't want to find it again when you search for inexact matches).
For example, given the target word guava and the user guess gulag, we expect the status message: GU-a-. We'll start by converting both the target and the guess into lists:
target: ['g','u','a','v','a'] guess: ['g','u','l','a','g']
Now, we'll check for exact matches, beginning from left to right in the guess list. "Does the first letter of 'gulag' match the first letter of 'guava'?" It does, so we'll capitalize the first letter of the guess list and we'll change the first letter of the target list to a period:
target: ['.','u','a','v','a'] guess: ['G','u','l','a','g']
Next, "Does the second letter of 'gulag' match the second letter of 'guava'?" It does again, so we'll capitalize the second letter of the guess list and we'll change the second letter of the target list to a period:
target: ['.','.','a','v','a'] guess: ['G','U','l','a','g']
Next, we'll ask if the third, fourth, or fifth letters match, and none will, so the two lists will remain unchanged.
We move on to finding inexact matches. For each letter in the guess list, we do the following:
Following this algorithm, we look at the first letter is the guess list: G. Since it's capitalized, we go on to the next letter: U. It, too, is capitalized, so we move on to the third letter, l, which is not in the target list, so we replace the letter in the guess list with a '-':
target: ['.','.','a','v','a'] guess: ['G','U','-','a','g']
The fourth letter in the guess list, a, is in the target list, so we replace the letter in the target list with a '.':
target: ['.','.','.','v','a'] guess: ['G','U','-','a','g']
The final letter in the guess list, g, is not in the target list, so replace the letter in the guess list with a '-':
target: ['.','.','.','v','a'] guess: ['G','U','-','a','-']
The guess list is now nearly the status information which you need to provide. You just need to join the letters in the list together to form the string 'GU-a-'.
Here is some sample output from three runs of a lingo program, notice the error handling:
$ python lingo.py @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ Welcome to Lingo Each turn you will try to guess the secret word If you guess the word, you win If you guess some letters in the word, lingo will display: guessed letters in the correct position in upper case guessed letters in the incorrect position in lower case Good Luck! @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ word: - - - - - Guess a 5 letter word: hello word: - e l - - Guess a 5 letter word: letter Invalid Input, enter a word with 5 characters. try again... Guess a 5 letter word: oops Invalid Input, enter a word with 5 characters. try again... Guess a 5 letter word: helpm Invalid Input, helpm is not a valid word. try again... Guess a 5 letter word: piles word: P I l E - Guess a 5 letter word: pixel You guessed the word in 3 tries. Congratulations! $ python lingo.py @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ Welcome to Lingo Each turn you will try to guess the secret word If you guess the word, you win If you guess some letters in the word, lingo will display: guessed letters in the correct position in upper case guessed letters in the incorrect position in lower case Good Luck! @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ word: - - - - - Guess a 5 letter word: snort word: - - - r - Guess a 5 letter word: retort Invalid Input, enter a word with 5 characters. try again... Guess a 5 letter word: great word: - r - a - Guess a 5 letter word: barks word: b A r - - Guess a 5 letter word: rstuv Invalid Input, rstuv is not a valid word. try again... Guess a 5 letter word: roles word: R - - - - Guess a 5 letter word: ramps word: R A - - - Guess a 5 letter word: rabid word: R A B i - Guess a 5 letter word: rabbi You guessed the word rabbi in 7 tries. Congratulations! $ python lingo.py @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ Welcome to Lingo Each turn you will try to guess the secret word If you guess the word, you win If you guess some letters in the word, lingo will display: guessed letters in the correct position in upper case guessed letters in the incorrect position in lower case Good Luck! @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ word: - - - - - Guess a 5 letter word: grill word: - - i l - Guess a 5 letter word: trips word: t - i p - Guess a 5 letter word: QUIT The word you were trying to guess is: plait Better luck next time!
Warning: When you get this working, be prepared to spend a while playing it. Lingo is remarkably addictive!
Once you are satisfied with your program, hand it in by typing handin21 in a terminal window.