STUDENT LESSON AB24 Recursive Array Programming
Java Curriculum for AP Computer Science, Student Lesson AB24 1 STUDENT LESSON AB24 Recursive Array Programming INTRODUCTION: Suppose that you are trapped inside a maze and you need to find your way out. Initial attempts at exiting are random and because the walls all appear identical, you begin wasting time and energy trying the same routes over and over again. After some thought and after recalling a useful computer science algorithm, you take advantage of a tool you have in your pocket - a marking pen. You begin marking the walls with some notes and a time stamp. (This technique recalls the one used by Hansel and Gretel in the Grimm fairy tale, when Hansel marked his path through the woods with shiny stones (and then breadcrumbs), so that he could safely find his way back.) At each branch point, you mark the direction you are about to attempt with an arrow. If a dead-end is encountered just around the corner, you retreat to the branch point, mark dead-end for that direction, and try another direction. By marking the directions that have failed, you avoid needlessly trying them again. This two-dimensional problem involving backtracking provides us with a recursive matrix problem (and its entire solution), translated from Oh! Pascal!, 2nd edition. 1 Your programming assignment will also be a recursive matrix problem. The key topics for this lesson are: A. Defining the Maze Problem B. Developing the Recursive Solution C. The Solution to the Maze Problem VOCABULARY: BACKTRACKING DISCUSSION: A. Defining the Maze Problem 1. The maze will be defined as a 2-D grid of asterisks (marking walls) and blanks (marking potential paths). The size of the grid will be 12 x 12 and the starting location will be at 6, 6. 2. The data structure for this problem will be a 2-dimensional array of char. The array will be declared as a 13 x 13 grid so that we can use locations 1..12 by 1..12. Row 0 and column 0 will not be used in the data structure. 1 Doug Cooper and Michael Clancy, Oh! Pascal! 2nd Edition, W. W. Norton & Company (New York and London), 1985, pp. 362-367.
Java Curriculum for AP Computer Science, Student Lesson AB24 2 3. The initial grid is stored as a text file and will be loaded into the array. (Here is a copy of the mazedata.txt file) 4. The solution is a backtracking algorithm involving a series of trial and error attempts. A potential path out of the maze will be traced with a!, with moves limited to horizontal or vertical directions. If a dead-end is encountered, back up and try a different direction. 5. We will be at an exit point if we arrive at row 1 or MAXROW, or at column 1 or MAXCOL. B. Developing the Recursive Solution 1. In developing a recursive solution, consider the base cases first. What situation(s) cause the recursive method to exit? a. We have arrived at a location that is off the data structure. It is important to catch this situation first to avoid an array indexing error. b. Encountering a '' character means that we have run into a wall. The algorithm should stop. c. Encountering a location we have already visited should cause the algorithm to stop. d. Arriving at a location that has a row or column value equal to 1 or MAXROW or MAXCOL means that we have found an exit point. 2. The general case of encountering a blank space requires the following steps: a. Change the character value from the blank space to the '!' character. b. Check to see if you are at an exit point. If so, print the maze with a trail of '!' markers to the exit point. c. If you are not at an exit point, make 4 recursive calls to check all 4 directions, feeding the new coordinates of the 4 neighboring cells. 3. When an exit point is found, print only the successful trail of '!' marks that leads to an exit. As a result, it is necessary for each recursive call to work with a copy of the array. Why is this? If a reference to the original array is
Java Curriculum for AP Computer Science, Student Lesson AB24 3 passed with each recursive call, the placement of '!' marks would be permanent in the data structure. C. The Solution to the Maze Problem import java.io.file; import java.util.scanner; import java.io.ioexception; Description of the Class @author Administrator @created July 16, 2002 class ThreadTheMaze{ Description of the Field private final static char BLANK = ' '; private static final int MAXROW = 12; private static final int MAXCOL = 12; private int mymaxrow; private int mymaxcol; private char [][] mymaze; public ThreadTheMaze(){ mymaze = new char [MAXROW + 1][MAXCOL + 1]; mymaxrow = mymaze.length - 1; mymaxcol = mymaze[0].length - 1; Initiates the trace process @param none public void dotracemaze() { loadmaze(); tracemaze(mymaze, mymaxrow/2, mymaxcol/2); Loads the maze characters from mazedata.txt @param maze Description of Parameter private void loadmaze(){ String line; Scanner in; try{ in = new Scanner(new File("mazeData.txt")); for (int row = 1; row <= mymaxrow; row++){ line = in.nextline(); for (int col = 1; col <= mymaxcol; col++){ mymaze[row][col] = line.charat(col-1);
Java Curriculum for AP Computer Science, Student Lesson AB24 4 catch(ioexception i){ System.out.println("Error: " + i.getmessage()); Description of the Method @param maze Description of Parameter public void printmaze(char[][] maze){ Scanner console = new Scanner(System.in); for (int row = 1; row <= mymaxrow; row++){ for (int col = 1; col <= mymaxcol; col++){ System.out.print("" + maze[row][col]); System.out.println(); System.out.println(); System.out.println("Hit enter to see if there are more solutions."); String anything = console.nextline(); Will attempt to find a path out of the maze. A path will be marked with the! marker. The method makes a copy of the array each time so that only the path out will be marked, otherwise extra! markers will appear in the answer. The function is recursive. @param maze Description of Parameter @param row Description of Parameter @param col Description of Parameter public void tracemaze(char[][] maze, int row, int col){ //char[][] mazecopy = (char[][])maze.clone(); char[][] mazecopy = new char[maze.length][maze[0].length]; for (int r = 0; r < mazecopy.length; r++){ for (int c = 0; c < mazecopy[0].length; c++){ mazecopy[r][c] = maze[r][c]; if (1 <= row && row <= mymaxrow && 1 <= col && col <= mymaxcol){ // boundary check, if false, a base case if (BLANK == mazecopy[row][col]){ // if false, base case mazecopy[row][col] = '!'; if (1 == row mymaxrow == row 1 == col mymaxcol == col){ printmaze(mazecopy); // base case else{ tracemaze(mazecopy, row - 1, col); tracemaze(mazecopy, row, col + 1);
Java Curriculum for AP Computer Science, Student Lesson AB24 5 tracemaze(mazecopy, row + 1, col); tracemaze(mazecopy, row, col - 1); Here are the two solutions when starting at location (6,6):!!!!!!!!!!!!!!!!!!!!!!!!! 1. It is very significant that a blank space be changed to an '!' mark before the recursive calls are made. For example, suppose you began at location 6,6 and a blank space was encountered. If you didn't change the blank to an '!' mark, the recursive call to solve the upward direction would receive the location 5,6. This recursive call would eventually look back down at location 6,6 - the location where it came from. A blank space would still be there and the recursive calls would go around in circles until the computer ran out of memory. 2. Changing the blank space to an '!' mark is like leaving a trail of markers. When a recursive call of a neighboring cell looks back at the cell from which it came, it will see a '!' mark and not a blank space. SUMMARY/ REVIEW: Some of the earlier examples of recursion were applied to linear problems. The factorial or Fibonacci problems were one dimensional, which required only one recursive call within the algorithm. The maze problem is best-solved recursively because of the different directions that the problem solving takes. Loosely stated, any problem that involves multiple directions and returning to a branch point is a likely candidate for recursion. ASSIGNMENT: Code from Lesson AB24.1, ThreadTheMaze.java, mazedata.txt Lab Assignment AB24.1, EraseObject Lab Assignment AB24.1, Data File, digital.txt Worksheet AB24.1, Recursive Arrays