Forest Fire – TCS CodeVita
Calculate the minimum time required for fire to spread from an initial tree to all trees in a forest, spreading to all 8 adjacent trees every minute
Understand the Problem
Problem Statement
Roco is an island near Africa which is very prone to forest fire. Forest fire destroys the complete forest. Not a single tree is left. This island has been cursed by God, and the curse is that whenever a tree catches fire, it passes the fire to all its adjacent trees in all 8 directions: North, South, East, West, North-East, North-West, South-East, and South-West. The fire spreads every minute in this manner, with every tree passing fire to its adjacent trees.
You are given a forest layout where T denotes tree and W denotes water. When a tree at position (X, Y) catches fire, it spreads to its 8 adjacent trees in the next minute, and this process continues until the entire forest is on fire.
Your task is to determine how long it would take for the entire forest to be on fire, given the location of the first tree that catches fire.
Constraints
- The forest dimensions are between 3 and 20 rows and columns: 3 <= M, N <= 20
- Coordinates are 1-indexed: 1 <= X <= M, 1 <= Y <= N
- The forest layout contains only characters 'T' (tree) and 'W' (water)
- The initial position (X, Y) must be a tree (not water)
- The forest is guaranteed to have at least one tree
- The entire forest is guaranteed to catch fire eventually
Examples
3 3
1 3
W T T
T W W
W T T5The fire starts at (1,3). In minute 1: (1,3) burns. In minute 2: (1,2) burns. In minute 3: (2,1) burns. In minute 4: (3,2) burns. In minute 5: (3,3) burns. It takes 5 minutes for all trees to catch fire.
6 6
1 6
W T T T T T
T W W W W W
W T T T T T
W W W W W T
T T T T T T
T W W W W W16The fire starts at (1,6) and spreads throughout the forest in a wave pattern. The furthest tree from the starting position takes 16 minutes to catch fire, which determines the total time required for the entire forest to burn.
Solution
#include <stdio.h>
#include <stdlib.h>
#define MAX_SIZE 21
// Structure to represent a position in the grid
struct Point {
int x, y;
};
// Queue structure for BFS
struct Queue {
int front, rear, size;
struct Point* array;
};
// Function to create a queue
struct Queue* createQueue(int capacity) {
struct Queue* queue = (struct Queue*)malloc(sizeof(struct Queue));
queue->front = queue->size = 0;
queue->rear = capacity - 1;
queue->array = (struct Point*)malloc(capacity * sizeof(struct Point));
return queue;
}
// Function to check if queue is full
int isFull(struct Queue* queue) {
return (queue->size == MAX_SIZE * MAX_SIZE);
}
// Function to check if queue is empty
int isEmpty(struct Queue* queue) {
return (queue->size == 0);
}
// Function to enqueue an item
void enqueue(struct Queue* queue, struct Point item) {
if (isFull(queue))
return;
queue->rear = (queue->rear + 1) % MAX_SIZE;
queue->array[queue->rear] = item;
queue->size = queue->size + 1;
}
// Function to dequeue an item
struct Point dequeue(struct Queue* queue) {
struct Point item = {0, 0};
if (isEmpty(queue))
return item;
item = queue->array[queue->front];
queue->front = (queue->front + 1) % MAX_SIZE;
queue->size = queue->size - 1;
return item;
}
// Function to check if a position is valid
int isValid(int x, int y, int m, int n) {
return (x >= 1 && x <= m && y >= 1 && y <= n);
}
// Function to solve the forest fire problem
int solveForestFire(char forest[MAX_SIZE][MAX_SIZE], int m, int n, int startX, int startY) {
// Directions for 8 adjacent positions
int dx[] = {-1, -1, -1, 0, 0, 1, 1, 1};
int dy[] = {-1, 0, 1, -1, 1, -1, 0, 1};
// Create queue for BFS
struct Queue* queue = createQueue(MAX_SIZE * MAX_SIZE);
// Visited array to track burned trees
int visited[MAX_SIZE][MAX_SIZE] = {0};
// Start BFS from the initial burning tree
struct Point start = {startX, startY};
enqueue(queue, start);
visited[startX][startY] = 1;
int minutes = 0;
int totalTrees = 0;
int burnedTrees = 0;
// Count total trees in the forest
for (int i = 1; i <= m; i++) {
for (int j = 1; j <= n; j++) {
if (forest[i][j] == 'T') {
totalTrees++;
}
}
}
// BFS to spread fire
while (!isEmpty(queue)) {
int currentLevelSize = queue->size;
// Process all trees that catch fire in this minute
for (int i = 0; i < currentLevelSize; i++) {
struct Point current = dequeue(queue);
burnedTrees++;
// Spread fire to all 8 adjacent trees
for (int dir = 0; dir < 8; dir++) {
int newX = current.x + dx[dir];
int newY = current.y + dy[dir];
if (isValid(newX, newY, m, n) &&
forest[newX][newY] == 'T' &&
!visited[newX][newY]) {
visited[newX][newY] = 1;
struct Point next = {newX, newY};
enqueue(queue, next);
}
}
}
// If there are more trees to burn, increment minutes
if (queue->size > 0) {
minutes++;
}
}
free(queue->array);
free(queue);
return minutes;
}
int main() {
int m, n;
int startX, startY;
char forest[MAX_SIZE][MAX_SIZE];
// Read input dimensions
scanf("%d %d", &m, &n);
// Read starting position
scanf("%d %d", &startX, &startY);
// Read forest layout
for (int i = 1; i <= m; i++) {
for (int j = 1; j <= n; j++) {
scanf(" %c", &forest[i][j]);
}
}
// Solve and print result
int result = solveForestFire(forest, m, n, startX, startY);
printf("%d\n", result);
return 0;
}The C solution implements BFS using a custom queue structure. The algorithm:
- Creates a queue to store positions of burning trees
- Initializes a visited array to track burned trees
- Starts BFS from the initial burning tree position
- Processes trees level by level, where each level represents one minute of fire spread
- For each burning tree, checks all 8 adjacent positions and adds unburned trees to the queue
- Counts the number of levels processed to get the total time
The solution handles the grid using 1-indexed coordinates as specified in the problem.