6.6 Bounds and Neighbors
Bounds Checking and Neighbors in a 2D Array
Unit 6: 2D Arrays and Tile Maps · Lesson 6.6 · about 35 minutes · no coding experience needed
Every grid game asks "what is next to me", and every edge cell has neighbors that do not exist. Handling that is one method, and the order of two tests inside it is the difference between working and crashing.
What you will be able to do
- Write a bounds check for a row and column
- Explain why the range tests must come before the lookup
- Use a bounds-checked lookup for wall collision
Words you will need
- In bounds
- In plain words This cell actually exists.
- More precisely Row and column both within the valid index ranges.
- Short circuit
- In plain words Java stops as soon as it knows the answer.
- More precisely && does not evaluate its right side when the left is false.
Build it step by step
Every step below leaves a scenario that compiles and runs. If you stop halfway you will have something that works, not something broken. Follow along in Greenfoot rather than reading straight through.
-
Step 1
On your screen A bounds-checking method with all four conditions.
public boolean inBounds(int row, int col) { return row >= 0 && row < map.length && col >= 0 && col < map[0].length; }Four tests, and all four are needed.
Row not negative, row not past the last row, column not negative, column not past the last column.
It returns a boolean, so it drops straight into an if, which is the 3.4 pattern. Naming it `inBounds` means the calling code says what it means.
-
Step 2
On your screen A combined check with the bounds test before the lookup, and a broken version with them the other way round.
// SAFE: the guard runs first if (inBounds(r, c) && map[r][c] == 1) { ... } // THROWS: the lookup happens before the guard can help if (map[r][c] == 1 && inBounds(r, c)) { ... }This is the payoff for short-circuit evaluation from 2.3, and it is a lovely piece of machinery.
In the safe version, if `inBounds` is false Java NEVER EVALUATES the right side, so the out-of-range lookup never happens.
In the broken version the lookup runs first and throws before the check can save you. Same two tests, opposite results, purely because of order.
-
Step 3
On your screen A grid with a highlighted cell and its four orthogonal neighbors, two of which are outside the grid.
int walls = 0; if (inBounds(row - 1, col) && map[row - 1][col] == 1) { walls++; } // up if (inBounds(row + 1, col) && map[row + 1][col] == 1) { walls++; } // down if (inBounds(row, col - 1) && map[row][col - 1] == 1) { walls++; } // left if (inBounds(row, col + 1) && map[row][col + 1] == 1) { walls++; } // rightThe four orthogonal neighbors. Up is row minus one, because row counts DOWNWARD, which is the same rule as y from 1.4.
A corner cell has two neighbors that do not exist, and the guard on every line is what stops that throwing. It is repetitive on purpose: at this stage clear beats clever.
-
Step 4
On your screen A player blocked by a wall, with the destination cell checked before the move.
public void tryMove(int dRow, int dCol) { int newRow = getY() + dRow; int newCol = getX() + dCol; if (world.inBounds(newRow, newCol) && world.tileAt(newRow, newCol) != 1) { setLocation(newCol, newRow); // swap again } }And this is grid-based wall collision, which is the mechanic Tile Dungeon is built on.
Work out where you WOULD go, check that cell exists and is not a wall, and only then move. No collision detection needed at all: the array already knows where the walls are.
Note `setLocation(newCol, newRow)`: the swap from 6.4, one last time.
Mistakes almost everyone makes here
These are the wrong ideas students actually build at this point. Read them even if you think you understand, because a wrong idea you have not noticed is the expensive kind.
Common wrong idea The bounds check can go after the lookup.
What is actually true The lookup throws before the check can run. Order is everything.
Why it matters The single most common way a bounds check fails to protect anything.
Common wrong idea Only the upper bound needs checking.
What is actually true Negative indexes throw too, and the cell above row 0 is negative.
Why it matters Half the edge cases are at the top and left.
Common wrong idea Up is row plus one.
What is actually true Up is row MINUS one, because rows count downward.
Why it matters The same inversion as y in 1.4, and it catches people again here.
Common wrong idea Wall collision needs isTouching.
What is actually true With a grid, look the destination up in the array. It is simpler and exact.
Why it matters Grid movement with pixel collision produces actors that half-enter walls.
Check your understanding
Answer these before moving on. They are graded instantly and you can retry.
-
1. Why must `inBounds(r, c)` come BEFORE `map[r][c]` in an &&?
-
2. Which is the cell ABOVE map[3][5]?
-
3. How many of the four tests in inBounds are needed?
-
4. A corner cell is asked for its four neighbors. What happens without guards?
-
5. In a grid game, how is wall collision best done?
Fill in the code
Write the bounds check. All four tests are needed, and the row is checked against the number of rows.
public boolean inBounds(int row, int col)
{
return row 0 && row < map.
&& col >= 0 && col map[0].length;
}
Stuck? Open a hint for each blank
- Blank 1: Row must not be negative, and zero itself is valid. Two characters.
- Blank 2: The number of rows.
- Blank 3: Must stop one before the column count. One character.
Lesson quiz
This one counts toward your progress. Take it when the section above makes sense.
-
1. `if (map[r][c] == 1 && inBounds(r, c))` is wrong because:
-
2. Why does `&&` make the safe version work?
-
3. The four neighbors of map[row][col] are at:
-
4. Grid-based wall collision works by:
The short version
- inBounds needs all four tests: row and column, lower and upper.
- The bounds check must come FIRST in the &&, or the lookup throws anyway.
- Up is row MINUS one. Rows count downward.
- Grid collision means checking the destination cell, not detecting overlap.
If you get stuck
These pages cover the problems that come up most often in this lesson. Opening one is not cheating and it is not counted against you.
Get in Touch
Whether you're a student, parent, or teacher — I'd love to hear from you.
Just want free AP CS resources?
Enter your email below and check the subscribe box — no message needed. Students get daily practice questions and study tips. Teachers get curriculum resources and teaching strategies.
Message Sent!
Thanks for reaching out. I'll get back to you within 24 hours.
Prefer email? Reach me directly at [email protected]