LAB 5 - Nim Game


OBJECTIVE:


DESCRIPTION.

In this lab we develop a program to play the classic game of Nim. The game starts with a row of skulls (Traditionally people use coins or stones). Let the number of skulls (numSkulls) be FIVE. Two players take turns to remove one, two or three skulls from the stack. The player to pick up the last skull loses.
The user should have an option to


Your program should start by displaying something interesting and atrocious like this:


    You, Mr. Smart, have been imprisoned by the vile
    Norwegian Ostrogoths.  The chieftain stands in front
    of you, stirring a bubbling cauldron.  He
    challenges you to a game - the game of
                       NIM!!!
    If you lose, you become human stew; if you win you
    can become an honorary member of the Ostrogoth
    tribe!!. There is a row of skulls on the table:

         00000
 
    There are FIVE skulls when the game starts. You and
    the chieftain will take turns - each of you can
    remove one, two or three skulls from the pile, and
    throw it into the cauldron.  If you are to move
    with only ONE skull on the table, then then you go
    into the cauldron with it!!

    The chieftain approaches the table with a big
    gloating grin and ONE, TWO, - he tosses two skulls
    into the cauldron. So this is what you have now:
 
         000
 
    The chieftain is leaning on the table, glaring at
    you. "So, Mr. Smart, what will your turn be?" he
    asks.  You lift your manacled arm and toss -
    How many skulls do you toss into the cauldron?
 

The user at this point should type in 1, 2, or 3. Inputs that are incorrect, or not in this range, should result in one of several randomized prompts like:
Oops - please type in a number between 1 and 3!!
> or
Hello Mr. Smart - english nahi samajhte kya? Your move must be a number between 1 and 3.
Or if the input is non-integer:
I am afraid you can't type alphabets or fractions - only whole numbers please.

Before the first move, the user may type "o" or "O" for Options - and he is then asked:
    Options Menu:

    Number of skulls (between 5 and MAXSKULLS) ?
     	[user types in a number]
    
    Who goes first (Human or Computer)?
    	[user types in something starting in "h","H", or "c","C".]

    Difficulty level (Simple or No Chance)?
	[user types in string beginning "s","S" or "n", "N"]

Incorrect input is sternly castigated.

And then the game proper begins!! Once the game starts, options cannot be changed.

At the end, if you manage to win, the program should congratulate you, or else if he wins, he should - ahem! - be as dastardly as a computer screen can be!

After the game is over, the score is printed (Human - 1, Computer - 0) - and the user is given the option to continue. ("Want to play another game? (Yes or No)).

Over multiple games, the score is maintained.

Your job in this program is to manage the game, and also to decide the computer's (chieftain's) response to your moves. Now Get to it!!



HOW TO PROGRAM IT

As you can tell, the program must keep track of the number of skulls on the table. This it does by an int variable, say numSkulls.

You can after some doodling figure out that one of the players can usually always win. (e.g. if there are 7, the first player can always win). But you must also have a simple move - which may be based on the taking a random number (e.g. System.currentTimeMillis()%2 + 1), - the important point is to be able to play the game at two levels.

One approach may be to define a class NimGame. This class should have some instance variables (like numSkulls, difficultyLevel), and methods like

etc. which do the obvious things. A main() method should create an instance of a NimGame, and will start and play the game, invoking other methods as needed. decideMove() chooses a move for the computer when it is the computer's turn.


READING INPUT FROM THE CONSOLE

The program InputLab5.java contains the code discussed in class on how to do I/O in Java. You should be able to adapt these to help you decipher the input you need. . .


PROGRAM DESIGN PROCESS

This is a complex program with many methods, so PLEASE SPEND SOME TIME BEFORE COMING TO THE LAB writing down the following steps. This may be considered as the DESIGN of your program. Once designed, the program is more easily coded:

  1. Identify all the variables that will be needed. Variables help to keep track of the state of the program. If something must be remembered, it must be accounted for as a variable.
  2. For each variable, identify its type, and if necessary, its initial value. This should complete your declarations.
  3. Break the program down into several sizeable pieces. It's not important to know immediately how each piece is implemented, but it is necessary to identify logically distinct portions of the program. For example, the instructions must be written at the beginning and the results at the end.
  4. Identify those parts of the program that are part of a conditional or looping construct, remembering the features that distinguish each of the loop types.
  5. Our informal design is completed if a reasonable person can follow the logical states of the program without doing anything that seems contrary to the imagined execution of the program.
  6. Armed with a design, it is now possible to implement each of the logical components in Java. It is often the case that the design had to be augmented to take into account the inner details.

  7. As you implement each of the logical components of the program, test these carefully to see if the program works as expected. For example, you run the program to see if the instructions and initial state is printed correctly. Then see if on incorrect input, the errors are handled properly. Test that the move made is actually reflected in the game state, etc.
  8. Once completed, test your program thoroughly. Does it work in short simulations (as seen in the one above)? Does it work when you follow the optimal solution?
  9. When completed, sit back, take pride in your work, and save your program.

VARIABLE NAMES, INDENTATION AND PROGRAMMING STYLE

Code should be clean, consistently indented. Variable names should be meaningful. Style conventions, such as parentheses alignment, no magic numbers etc must be followed. The lab must be loaded to your home page and will be evaluated based on an online demo-run and offline evaluation of coding practice.



THOUGHT QUESTIONS.

Consider the following questions as you complete the lab: (not to be submitted)
  1. In your finished program, are there any unnecessary variables?

  2. Are there any statements that don't get executed?

  3. Return to this code a couple of days later. Are there improvements you can see after this fresh view of your code?

  4. Is your game at the MostDifficultLevel playing the best game possible? Is this true for ALL possible game situations?

  5. Suppose there were three players. Is there a set of rules that can decide who will win?

  6. How might you implement this program using a windows GUI with buttons and graphics?