Lab #4: Arrays
Fall 2000
You must submit this lab by 11:59pm Wednesday, October 18. Yes, this is a 2 week lab!
To gain experience with the use and manipulation of arrays. You will also use more methods and practise more thorough testing. This is a longer program than your previous labs, so be sure to start it early.
For this lab, you are to write a program which permits two players to play a simplified game of checkers. The game will be played using red and white game pieces on an 8 by 8 square checkerboard, initially set up according to the following diagram.
Moves: 0
Score: Red 12 White 12
0 1 2 3 4 5 6 7
B: 0 r r r r 0
B: 1 r r r r 1
B: 2 r r r r 2
B: 3 . . . . 3
B: 4 . . . . 4
B: 5 w w w w 5
B: 6 w w w w 6
B: 7 w w w w 7
0 1 2 3 4 5 6 7
The squares on the board are identified using row,column coordinates, with the row indicated first and then followed by the column. There are coordinates printed along all sides of the board to help you determine the location of a game piece. The game pieces at 2,6, 1,7, 0,0 are all red. The piece at 7,1 is white. The TOP LEFT corner is at location 0,0 and the BOTTOM RIGHT corner is at 7,7.
The squares contain a single character to indicate the state of the game board:
Notice the dark squares are always on even values of row + column. This always gives you a dark square on the player's own right corner. Game pieces are only played on the dark squares.
It is important that you print out your checker board in exactly the same fashion shown above. The "B: " must be placed at the beginning of the line, and the row, and column numbers must be printed in the same way. Be sure to get the extra spacing right between the columns too (a single space character). At the top of every board is a move count, which goes up by one after every player move. As well, a score is printed, showing how many red and white pieces remain on the board (kings count as 2, see below).
The red player begins the game by sliding a red piece one position, to an empty dark square (marked by a period '.'). The moving of the game piece uncovers a new empty dark square in the old position. No game piece should ever move onto a white square (marked by a space character ' '). After that, players alternate turns, moving their pieces across the board. When entering a move, four values will always be required. Check the validity of the coordinates (and of the move) after accepting all four values. If the move is not valid, ask the user to try again after printing the following string:
"ERROR invalid move"
In order to keep this lab simple and markable, your program must enforce the following rules (and no more!):
When the game is over, you must print the score and final board and determine the winner. Be sure to print the name of the winner, using one of the following strings:
"Red player wins" "White player wins" "Both players win"
You might find it fun to continue and add more of the basic checkers rules (multiple jumps, kings moving backwards, forced jumps, and so on), but you must not submit a program with these extra rules. Doing so will certainly result in a poor mark, despite your extra efforts. At a later time, such as during your project, you may be interested in rewriting this game as an applet to use graphics or even include a computer-based player. At that point, you might be able to use the extra rules you experiment with now.
To assist you in structuring your program, you must use the following file as a starting point:
(also:/share/copy/aps105/Lab4.java)
This file contains a set of stub methods that you can complete to obtain a solution to the lab. They are called stubs because they contain the smallest piece of dummy code possible to get the program to compile without syntax errors. You will replace the stubs with real code later. Work on one method at a time.
If you desire, you may add additional methods to the class. However, do not modify, add, or delete any parameters to the given methods. As well, do not delete any of the given methods.
The code we are giving you is actually a code specification that you must adhere to. This specification is often called the API, or Application Programming Interface, to your program.
By writing a clear API specification, we can write our own test program and actually call the methods in your program. We can send specific input into your methods, and then check the result it gives back. This type of testing is often called black box testing, because your code is being treated as a magical "black box" that we cannot look inside. Instead, the black box tester sends input and examines the output.
Moves: 0
Score: Red 12 White 12
0 1 2 3 4 5 6 7
B: 0 r r r r 0
B: 1 r r r r 1
B: 2 r r r r 2
B: 3 . . . . 3
B: 4 . . . . 4
B: 5 w w w w 5
B: 6 w w w w 6
B: 7 w w w w 7
0 1 2 3 4 5 6 7
When testing your program, you will find it useful to exploit the
operating system's pipe facility. A pipeline connects the
output of one program to become the input of another. By using the
cat command, you can print the contents of a file to
the screen. Using a pipe, represented with the symbol |,
you can send the output of cat into your Java
application instead, as if you had typed it at the keyboard yourself.
For example, suppose you create the file, moves.long
(using your editor) with the following contents:
2 6 3 7 -1 -1 -1 -1You can then use this file to play the game with the command:
computer.ecf% cat moves.long | java Checkers
Note that the methods of the Stdin class read a complete line every time they are called, therefore requiring each individual input to be on a separate line. The example file contains two different moves: the first move source 2,6, the destination 3,7; and the game ending move source -1,-1 and destination -1,-1. The final board would look like this:
Moves: 1
Score: Red 12 White 12
0 1 2 3 4 5 6 7
B: 0 r r r r 0
B: 1 r r r r 1
B: 2 r r r . 2
B: 3 . . . r 3
B: 4 . . . . 4
B: 5 w w w w 5
B: 6 w w w w 6
B: 7 w w w w 7
0 1 2 3 4 5 6 7
This input format can be a tedious and lengthy file which is difficult to edit, especially when you fall asleep at the keyboard and accidentally insert one extra number, misaligning everything. It is much better to create your test moves in an easier-to-read file first, say moves.easy, then convert it to the longer file moves.long using the command given below. The moves.easy file, and the game board after these moves, are shown below:
0 0 0 0 This is an invalid move. I used this move to 0 0 0 0 demonstrate what comments look like in this file. 0 0 0 0 Comments begin after the fourth 'space' on the line, 0 0 0 0 and go to the end of a line. 0 0 0 0 2 6 3 7 first move (red player always moves first) 3 7 2 6 white move error -- cannot move red piece (also a backward move!) 3 7 4 6 white move error -- cannot move red piece forward 5 7 4 6 white move 2 6 3 7 red move error -- no red piece there 2 4 3 5 red move 4 6 2 4 white jumps over red, capture! 1 7 2 6 red move, does not do the "forced jump" move (1,3 to 3,5). -1 -1 -1 -1 all done!
The final game board after these moves looks like this:
Moves: 5
Score: Red 11 White 12
0 1 2 3 4 5 6 7
B: 0 r r r r 0
B: 1 r r r . 1
B: 2 r r w r 2
B: 3 . . . r 3
B: 4 . . . . 4
B: 5 w w w . 5
B: 6 w w w w 6
B: 7 w w w w 7
0 1 2 3 4 5 6 7
Final Score
Red player: 11
White player: 12
White player wins
Here are the commands to convert this format to the longer moves.long, and then use that file as input to your program:
computer.ecf% awk ' { print $1; print $2; print $3; print $4 } ' < moves.easy > moves.long
computer.ecf% cat moves.long | java Checkers | less
In the command above, we also show the command 'less' being used to
slow up the output of your program, one screenful at a time.
You can just hit the space bar to go to the next page of output,
or press the 'u' key to scroll back one page. Pressing 'q' quits.
Also, note that Java does not display the input when it is received through a pipe. Instead, you may find it useful to add an extra println statement to print the user move before printing the updated game board.
As part of writing a larger program, you will find that thorough testing is a very important part of getting it to work. It is important that you test all corner cases in your code, because if they aren't tested there is likely a bug hidden in there.
There should probably be at least one (even minor) test case for every if(), else, while(), and for() word in your program. If you use && or ||, you are likely adding more test cases. Major test cases should be created to verify how these things fit together.
To ensure that you formalize your testing, you must submit two test cases named test0.easy and test1.easy:
To cultivate good programming habits, for this lab only we encourage you to share your test cases with your friends. This will give you more test cases than you can generate on your own, but it is not intended to replace your own careful thinking of good test cases. Although you are sharing them, the test cases you submit must be your own unique work -- do not confuse your test cases with those of your friend. Please note that their test cases may not properly or adequately test your checkers program.
Again, as in all labs, everything you submit must be your own work, including: test0.easy, test1.easy, and Checkers.java.
This section contains useful information about testing and how it relates to engineering as a profession, but it is not a specific component of your lab.
One reason that a large program like Windows crashes so often is because the programmers focus too much time on ``adding new features'' rather than extensively testing corner cases. This is not sound software engineering, and you must not begin to fall into the same chasm. You must test every piece of code you write. By doing incremental testing as you go along, you verify that the little pieces are working correctly. When you place them all together, you will have greater confidence that the program will work as a whole.
There is no money in fixing software bugs, only pride and marks!!!
You are studying engineering now, and one principle of engineering is that you will be held accountable for mistakes in your work. You must also maintain high ethical standards, which goes beyond basic law to state that you must not knowingly, through your action or inaction, cause public harm or not protect the public interest. Between 1985 and 1987, four cancer patients died while undergoing treatment due to lethal overdoses of radiation caused by a software bug. Do not write buggy software! To read more about the dangerous consequences of some software bugs, see: http://coverage.cnet.com/Content/Features/Dlife/Bugs/ss02.html
The concept of accountability for your engineering work comes from the legal system of tort law, meaning somebody can sue you for negligence or breach of contract. Unfortunately, software engineering is not yet a formally recognized engineering discipline by the Professional Engineers of Ontario (PEO), the governing body of engineering in this province. However, you can only call yourself an engineer if you are registered as a professional engineer (P.Eng.) with them. Here is their website: http://www.peo.on.ca/. You will find a number of links to your legal obligations as an engineer here http://www.peo.on.ca/EngPractice/guidelines.htm.
To sum it all up, although most software companies make a lot of money selling buggy programs, as an engineer you may find yourself financially responsible when someone begins legal action to sue you, or ethically bound to do the right thing. There is active work to try and include software engineering as a recognized part of the PEO and other professional engineering governing bodies.
This section will be expanded as questions are asked on the newsgroup. The body of the lab will remain constant, unless there are grave errors to be fixed (and noted here).
You must submit your Checkers.java, Stdin.java, and your 2 testing files, test0.easy and test1.easy. Please submit your easy-to-read test cases. We will convert them. If you wrote any other classes, place them in their own .java file and submit them as well.
computer.ecf% submitaps105f 4 Checkers.java Stdin.java test0.easy test1.easy