What if you could count all islands on a map perfectly without missing a single one or counting twice?
Why Number of Islands BFS and DFS in DSA Rust?
Imagine you have a big map made of squares, where some squares are water and some are land. You want to count how many separate islands of land there are. Doing this by looking at each square and trying to remember which ones you already counted is like trying to count friends in a crowded room without any system.
Manually checking each square and remembering which lands belong to which island is slow and confusing. You might count the same island twice or miss some parts. It's easy to get lost and make mistakes, especially when islands are close or oddly shaped.
Using BFS (Breadth-First Search) or DFS (Depth-First Search) helps you explore each island fully before moving to the next. These methods systematically visit all connected land squares, marking them as counted, so you never double count or miss any part.
let mut count = 0; for i in 0..rows { for j in 0..cols { if grid[i][j] == '1' { count += 1; // but no way to mark visited } } }
fn dfs(grid: &mut Vec<Vec<char>>, i: usize, j: usize) {
if i >= grid.len() || j >= grid[0].len() || grid[i][j] == '0' {
return;
}
grid[i][j] = '0';
if i > 0 { dfs(grid, i - 1, j); }
dfs(grid, i + 1, j);
if j > 0 { dfs(grid, i, j - 1); }
dfs(grid, i, j + 1);
}
let mut count = 0;
for i in 0..rows {
for j in 0..cols {
if grid[i][j] == '1' {
dfs(&mut grid, i, j);
count += 1;
}
}
}It enables you to quickly and correctly count all islands, no matter how complex their shapes or sizes, without missing or double counting any.
Think of a drone flying over a flooded area taking pictures. It needs to count how many separate dry land patches (islands) are left to plan rescue operations. BFS or DFS helps the drone's software do this accurately and fast.
Manual counting is confusing and error-prone.
BFS and DFS explore connected lands fully to avoid mistakes.
This method helps count islands quickly and correctly.
Practice
Solution
Step 1: Understand the grid content
The grid contains '1's representing land and '0's representing water.Step 2: Define the problem goal
The problem asks to count how many separate groups of connected '1's exist, called islands.Final Answer:
Count how many groups of connected '1's (islands) are in the grid -> Option CQuick Check:
Number of islands = count of connected '1' groups [OK]
- Confusing island count with largest island size
- Counting '0's instead of '1's
- Calculating perimeter instead of count
Solution
Step 1: Identify correct data type for grid
The grid should be a 2D vector of chars because the problem uses '1' and '0' as characters.Step 2: Check syntax for 2D vector initialization
let grid: Vec = vec![vec!['1', '0'], vec!['0', '1']]; uses Vec with vec! macro and char literals '1' and '0', which is correct Rust syntax.Final Answer:
let grid: Vec = vec![vec!['1', '0'], vec!['0', '1']]; -> Option BQuick Check:
2D vector of chars with vec! and '1'/'0' chars [OK]
- Using integer types instead of char
- Using arrays without specifying type
- Using 1D vector instead of 2D
fn main() {
let mut grid = vec![
vec!['1', '1', '0', '0'],
vec!['1', '0', '0', '1'],
vec!['0', '0', '1', '1'],
vec!['0', '0', '0', '0'],
];
println!("{}", num_islands(&mut grid));
}
fn num_islands(grid: &mut Vec) -> i32 {
let mut count = 0;
for i in 0..grid.len() {
for j in 0..grid[0].len() {
if grid[i][j] == '1' {
dfs(grid, i, j);
count += 1;
}
}
}
count
}
fn dfs(grid: &mut Vec, i: usize, j: usize) {
if i >= grid.len() || j >= grid[0].len() || grid[i][j] == '0' {
return;
}
grid[i][j] = '0';
if i > 0 { dfs(grid, i - 1, j); }
dfs(grid, i + 1, j);
if j > 0 { dfs(grid, i, j - 1); }
dfs(grid, i, j + 1);
}Solution
Step 1: Identify islands in the grid
The grid has these islands: - Top-left corner: (0,0),(0,1),(1,0) - Single '1' at (1,3) - Connected '1's at (2,2),(2,3)Step 2: Count islands after DFS marks visited
DFS marks connected '1's as '0' to avoid recounting. Total islands found = 3.Final Answer:
3 -> Option DQuick Check:
Count connected groups = 3 [OK]
- Counting diagonal connections as islands
- Not marking visited cells
- Off-by-one errors in loops
fn dfs(grid: &mut Vec, i: usize, j: usize) {
if i > grid.len() || j > grid[0].len() || grid[i][j] == '0' {
return;
}
grid[i][j] = '0';
if i > 0 { dfs(grid, i - 1, j); }
dfs(grid, i + 1, j);
if j > 0 { dfs(grid, i, j - 1); }
dfs(grid, i, j + 1);
}Solution
Step 1: Analyze boundary condition in DFS
The code checks if i > grid.len() or j > grid[0].len(), but valid indices go up to len()-1, so i == len() is out-of-bounds.Step 2: Correct boundary check to prevent panic
Use i >= grid.len() and j >= grid[0].len() to avoid accessing invalid indices and crashing.Final Answer:
The boundary check uses '>' instead of '>=' causing out-of-bounds panic -> Option AQuick Check:
Use >= for boundary checks to avoid panic [OK]
- Using > instead of >= in boundary checks
- Forgetting to mark visited cells
- Ignoring out-of-bounds errors
Solution
Step 1: Understand BFS traversal for islands
BFS visits all connected '1's in an island. Counting visited nodes during BFS gives island size.Step 2: Track and update largest island size
Maintain a counter inside BFS for current island size, update max size after BFS completes for each island.Final Answer:
Add a counter inside BFS to count connected '1's and track max size -> Option AQuick Check:
Count nodes during BFS to find largest island size [OK]
- Counting '1's before BFS (not island size)
- Using DFS without counting size
- Returning count of '0's instead of island size
Ready to prove it?
Pass the test and this pattern moves unknown
