CPS 006X, Fall 2003, Jotto

In Jotto each player tries to guess his opponent's secret five letter word. The game is similar to Mastermind in that each guess results in learning how many letters the guess has in common with the secret five letter word. Mastermind is played with colored pegs while Jotto is played with words --- and in Jotto the position of letters in common is not important, just the number of letters the secret word and a user's guess have in common.

For this assignment you'll write three programs (for each of the three you're given some code with which to start.)

  1. A function named commonCount that will be in jottotools.cpp and whose specification is given below. You'll test this function with jottotest.cpp to ensure that the function you write works as specified.

  2. A program implemented in jottoplay.cpp that lets the user guess the computer's secret word. For extra credit you'll modify this program to play over the web.

  3. A program implemented in jottoguess.cpp in which the computer tries to guess the user's secret word.

Files

You'll be using these source code files (and a Makefile, and a file of five-letter words).

If you're using Eclipse, snarf the jotto assignment. If you're programming with xemacs/command-line in Unix, copy the files using the commands below.

If you're using Eclipse you'll need to uncomment a line in main for both jottoplay.cpp and jottoguess.cpp that specifies a file name. Use the complete path version of the call to load a file. Do NOT modify/uncomment if you're running from the command-line.

In your cps006x directory (created when you ran the setup script), you should create an assign3 directory to work in. You'll then copy files into this directory to help you get started. That is, type the following unix commands from your account after you login (don't forget the trailing dot on the last line).

cd cd cps006x mkdir assign3 cd assign3 cp ~ola/cps006x/assign3/* .

Note that the last line has a dot at the end.

After you execute these commands, if you type pwd and ls you should see the name of the directory (which is assign3) and, after typing ls, the names of the files you copied which are given above.


  1. Implementing commonCount in jottotools.cpp
  2. (this part is worth 10 points)

    You'll implement one function, commonCount, as described below. To compile the function you'll use make via the command-line as follows:

       make jottotest
    
    
    If you're using Eclipse you'll need to add a make target of jottotest using the Eclipse make tutorial for help.

    You should also add a few tests to those provided in main of jottotest.cpp before submitting --- the tests you add should be useful in ensuring your code for commonCount works as specified.

    To illustrate what happens with a guess, suppose the secret word is "horse". For each of four different guesses, the number of letters in common is shown in the table below.

    Jotto Guesses and Responses
    guess common letters count
    mirth r,h 2
    moose o,s,e 3
    short s,h,o,r 4
    seems s,e 2

    Once a particular letter is counted as in common, it cannot be counted again. Note in the table above that "seems" has only two letters in common with "horse".

    You can see more examples of how counting letters in common between two words should work by looking at the tests in jottotest.cpp. You'll use this program, which calls the function commonCount that you'll design and implement in jottotools.cpp.

    Here's the header for commonCount, this header appears in jottotools.h, note that it's a prototype (has a semi-colon after it), but the code you write in the .cpp file is a complete function.

    
    int commonCount(string a, string b);
    // post: returns # characters in common to strings a and b    
    
    
    In implementing the function commonCount you'll need some way to avoid counting a letter more than once if it's in common to both words. There are two ways to do this:

    1. Use the string method replace examples of which can be found in stringreplace.cpp (a run and explanation are given below).

    2. Use the bracket [] operator to index a string and replace a character (see below).

    The string::replace method

    Here's the output when running the executable from stringreplace.cpp:

    
      scare
      score
      store
      storage
      storkage         (ok, not a word, but illustrates the method)
    
    
    The first argument to replace specifies the position at which the replacement starts (indexing beginning with zero). The second argument specifies how many characters of the string will be removed. The third argument specifies which string will be inserted at the location indicated by the first argument (after any removal has occurred).

    For purposes of replacing a character by another, the second argument in the call to method replace should be 1, and the third argument will be a single-character string that doesn't normally occur in words, e.g., something like "@".

    The string [] operator

    Strings can be indexed like vectors/arrays. This means the code below prints yes jello when run.
    
      string s = "hello";
      if (s[1] == 'h') cout << "yes";
      s[0] = 'j';
      cout << s << endl;
    
    
    Note that indexing can be used to access a character to check its value and to assign a new value. In both cases a char value is used (see the single quotes) rather than a string value.


  3. User Guesses the Computer's Secret Word jottoplay.cpp
  4. (this part is worth 20 points)

    To have the user play Jotto you'll write code in jottoplay.cpp to play a game. You'll need to use the class Jotto which is specified in jotto.h and implemented in jotto.cpp. An example of its use is given in the jottoplay.cpp file you're given, and which you'll modify.

    Here are some runs illustrating how your program might appear to the user. Take this run as a guideline, not a requirement, of how your program should work. If you run from Eclipse you won't type the name of the program as shown below (since you'll click on the program rather than type its name at the command line). User entered input is in italics

       prompt> ./jottoplay
       
       guess: fruit
       1       fruit 1
       
       guess: snake 
       2       snake 2
       
       guess: piano
       3       piano 3
       
       guess: sonic 
       4       sonic 2
       
       guess: panic
       5       panic 2
       
       guess: snack
       6       snack 2
       
       guess: manor
       7       manor 3
       
       guess: boast
       8       boast 2
       
       guess: slide
       9       slide 0
       
       guess: guano
       10      guano 5
    
    You win!!!
    
    
    Here's another run from a working program.
    
       prompt> ./jottoplay
       
       guess: brown
       1       brown 0
       
       guess: plaid
       2       plaid 2
       
       guess: dowel
       3       dowel 1
       
       guess: prawn
       not in my dictionary, try another word
       
       guess: brine
       4       brine 0
       
       guess: fruit
       5       fruit 0
       
       guess: track
       6       track 1
       
       guess: ghost
       7       ghost 2
       
       guess: sharp
       8       sharp 2
       
       guess: stale
       9       stale 3
       
       guess: lasts
       10      lasts 4
       
       
        You lose, the secret word was: glass
    

    Using the Jotto class and Playing a Game

    The program you write should allow the user to make 15 guesses. If the word hasn't been guessed it should be revealed to the user (in the run shown above the user was only allowed 10 guesses, you may want to use a number lower than 15 when testing.)

    The class Jotto, whose header is in jotto.h and reproduced below, allows you to get a random (secret) word and to check if a word the user enters is in the dictionary. The dictionary is loaded via the Jotto::loadWords method.

    class Jotto
    {
      public:
        Jotto();
        void loadWords(string filename);  // read a file of words
        string getSecretWord();           // select word at random
        bool contains(string word);       // true iff word in dictionary
    
      private:
        // not shown
    };
    
    

    Here are two runs of the version of jottoplay.cpp that you're given (user entered input in italics). The code shows how to use the Jotto class.

    To compile this program you type at the commandline:

      make jottoplay
    

    Or use Eclipse and add a make target of jottoplay as described in the Eclipse make tutorial.

    If you're using Eclipse, you won't enter the name of the program on the command line as shown below, you'll click the executable to run it.

       prompt> ./jottoplay
       
       Some secret words
       0       levee
       1       anger
       2       quota
       3       blare
       4       dukes
       5       faint
       6       pasts
       7       theft
       8       agate
       9       bolts
       enter a word: fruit
       fruit is in dictionary
       enter a word: snags
       snags NOT in dictionary
       enter a word: truck
       truck is in dictionary
       
       another run here
       
       prompt> ./jottoplay
       
       Some secret words
       0       niche
       1       blimp
       2       based
       3       bevel
       4       frame
       5       forks
       6       wires
       7       bayou
       8       minis
       9       brine
       enter a word: poops
       poops NOT in dictionary
       enter a word: snoop
       snoop is in dictionary
       enter a word: caret
       caret is in dictionary
    

    You should modify the code in jottoplay.cpp so that the user tries to guess the computer's secret word as shown in the sample runs above.

    The user gets at most 15 guesses. Words not in the dictionary should not count towards these 15 and should not be reported back as having letters in common with the secret word.

    Extra Credit CGI over the web Jotto

    Instructions soon...

  5. Computer Guesses User's word
  6. (this part is worth 20 points)

    If you try to guess the computer's word you'll need to reason carefully about guesses, letters in common, make strategic decisions about the likeliness of certain letters, etc. In the code you wrote in the previous part, you (the user) did this and the computer simply reported the number of letters in common for your guess and the computer's secret word.

    There's a straightforward method for getting the computer to guess your secret word that relies on the speed of the computer and its ability to query a dictionary of words. In this program the computer guesses the secret word you're thinking of.

    To implement this idea, you'll need to write the function getGuess and add significant code to the function play in the program jottoguess.cpp

    A sample run of jottoguess.cpp is shown below where the user's secret word is "gripe". User entered data is in italics (where 6 indicates the word has been guessed).

       I guess the word: aback
       how many letters in common? 0
       I guess the word: deeds
       how many letters in common? 1
       I guess the word: digit
       how many letters in common? 2
       I guess the word: dimly
       how many letters in common? 1
       I guess the word: dough
       how many letters in common? 1
       I guess the word: feign
       how many letters in common? 3
       I guess the word: giver
       how many letters in common? 4
       I guess the word: gripe
       how many letters in common? 6
    
       I win! it took me 8 guesses to find your word.
    
    
    Here's another run where the user makes a mistake. The user's secret word is "fruit".
       I guess the word: aback
       how many letters in common? 0
       I guess the word: deeds
       how many letters in common? 0
       I guess the word: fifth
       how many letters in common? 2        mistake, should be 3
       I guess the word: filly
       how many letters in common? 2
       I guess the word: fluff
       how many letters in common? 2
       I guess the word: fungi
       how many letters in common? 3
       I guess the word: guilt
       how many letters in common? 3
    
       I give up, what's your word? fruit
       I think you made a mistake!
       check your responses to my guesses
    
    

    In the code you'll write you'll ensure that that computer only guesses a word that could be the secret word. Initially any word will do, but after each guess words that cannot be the secret word are "crossed off" the computer's list of words that can be guessed.

    Crossing Off Words

    In the code you're given in jottoguess.cpp a vector of words is read from a file. In the code you'll write, you must maintain a parallel bool vector whose values indicate whether a string in the corresponding position of the word vector can be the secret word. Here's a diagram where initially there are six words in the dictionary and all could be the secret word.

    string vector bool vector
    "strap" true
    "train" true
    "turns" true
    "vague" true
    "whale" true
    "zebra" true

    Suppose the user's secret word is "whale". The computer initially guesses "strap" since this is the first word that might be the secret word --- since the corresponding bool value is true. The number of letters in common between "whale" and "strap" is reported by the user as 1. The computer program now eliminates any word from its dictionary that doesn't have one letter in common with "strap" (and the computer eliminates "strap" since it has been guessed.)

    string vector bool vector reason
    "strap" false guessed
    "train" false 3 in common with strap, not 1
    "turns" false 3 in common with strap, not 1
    "vague" true 1 in common with strap
    "whale" true 1 in common with strap
    "zebra" false 2 in common with strap, not 1

    Now the computer will guess "vague" since there are only two words that can be the secret word, and "vague" occurs first in the vector.

    The user will report that "vague" has 2 letters in common with the secret word "whale". The next time the computer will guess "whale" since that's the only word left for which the corresponding bool vector has a value of true.

    The Code You Write

    You must write code to ensure that only words that can be the secret word are guessed by the computer each time and that the bool values are set to false correctly after the user reports the number of letters in common between the guessed word and the secret word.

    Your program must allow some signal from the user that the word has been guessed. Entering 6 for number of letters in common is used in the program above, this is what your code should use.

Grading and Submitting

This assignment is worth 55 points.

If you submit more than once, be sure to submit all your .cpp files and your README file every time you submit.

In your README you should include how long you spent on this assignment, the names of people you spoke to about the assignment, and your impressions of the assignment (what was its purpose, did you enjoy it, etc.)

criteria points
commonCount and test 10
works correctly and has good tests
jottoplay.cpp 20
works correctly and is well written (equal)
jottoguess 20
works correctly and is well written (equal)
README 5

Use Eclipse to submit as assign3 be sure to submit all .h and .cpp files, even if you didn't modify them. Don't forget to submit a README too.

  submit_cps006x assign3 *.h *.cpp README

Owen L. Astrachan
Last modified: Sat Oct 4 21:41:43 EDT 2003