Geek in a Maze

Last Updated : 23 Jul, 2025

Geek is in a maze of size N * M. Each cell in the maze is made of either '.' or '#'. An empty cell is represented by '.' and an obstacle is represented by '#'. The task is to find out how many different empty cells he can pass through If Geek starts at cell (R, C) and avoids the obstacles and he can move in any of the four directions but he can move up at most U times and he can move down at most D times. 

Examples:

Input: N = 3, M = 3, 
R = 1, C = 0
U = 1, D = 1
mat = {{. . .}, {. # .}, {# . .}}
Output: 5
Explanation: Geek can reach 
(1, 0), (0, 0), (0, 1), (0, 2), (1, 2) 

Input: N = 3, M = 4, R = 1, C = 0, U = 1, D = 2 
mat = {{. . .},  {. # .}, {. . .}, {# . .}} 
Output: 10
Explanation: Geek can reach all the 
cells except for the obstacles.

Try It Yourself
redirect icon

[Naive Approach] Using Backtracking

The idea is to use backtracking with depth-first search (DFS) to explore all possible paths from the starting position. At each step, we temporarily mark the current cell as an obstacle to prevent cycles during the recursive exploration, then restore it when backtracking. We maintain counters for remaining up and down movements, decrementing them accordingly when moving in those directions. As we explore, we mark each reachable cell in a separate visited matrix, which helps us count unique cells at the end.

C++
// C++ program to solve Geek in a Maze problem
#include <bits/stdc++.h>
using namespace std;

void dfs(int r, int c, int u, int d, vector<vector<char>> &mat, 
vector<vector<bool>> &visited) {
            
    int n = mat.size(), m = mat[0].size();        
            
    // If out of bounds or obstacle or already visited, return
    if(r < 0 || c < 0 || r >= n || c >= m || mat[r][c] == '#')
        return;
    
    // Mark the cell as visited
    visited[r][c] = true;
    
    mat[r][c] = '#';
    
    // Explore in all four directions
    // Up
    if(u > 0)
        dfs(r-1, c, u-1, d, mat, visited);
        
    // Down
    if(d > 0)
        dfs(r+1, c, u, d-1, mat, visited);
        
    // Left
    dfs(r, c-1, u, d, mat, visited);
    
    // Right
    dfs(r, c+1, u, d, mat, visited);
    
    mat[r][c] = '.';
}

int numberOfCells(int r, int c, int u, int d, vector<vector<char>> &mat) {
    int n = mat.size(), m = mat[0].size();
    
    // Create a visited array to keep track of visited cells
    vector<vector<bool>> visited(n, vector<bool>(m, false));
    
    // Check if starting position is valid
    if(r < 0 || c < 0 || r >= n || c >= m || mat[r][c] == '#')
        return 0;
    
    // Run DFS from starting position
    dfs(r, c, u, d, mat, visited);
    
    // Return the number of unique cells
    int ans = 0;
    for (int i=0; i<n; i++) {
        for (int j=0; j<m; j++) {
            if (visited[i][j]) ans++;
        }
    }
    
    return ans;
}

int main() {
    vector<vector<char>> mat = 
      {{'.', '.', '.'},
       {'.', '#', '.'},
       {'#', '.', '.'}};
       
    int r = 1, c = 0;
    int u = 1, d = 1;
    
    cout << numberOfCells(r, c, u, d, mat);
    
    return 0;
}
Java
// Java program to solve Geek in a Maze problem
import java.util.*;

class GfG {
    
    static void dfs(int r, int c, int u, int d, char[][] mat, boolean[][] visited) {
        int n = mat.length, m = mat[0].length;        
            
        // If out of bounds or obstacle or already visited, return
        if(r < 0 || c < 0 || r >= n || c >= m || mat[r][c] == '#')
            return;
        
        // Mark the cell as visited
        visited[r][c] = true;
        
        mat[r][c] = '#';
        
        // Explore in all four directions
        // Up
        if(u > 0)
            dfs(r-1, c, u-1, d, mat, visited);
            
        // Down
        if(d > 0)
            dfs(r+1, c, u, d-1, mat, visited);
            
        // Left
        dfs(r, c-1, u, d, mat, visited);
        
        // Right
        dfs(r, c+1, u, d, mat, visited);
        
        mat[r][c] = '.';
    }

    static int numberOfCells(int r, int c, int u, int d, char[][] mat) {
        int n = mat.length, m = mat[0].length;
        
        // Create a visited array to keep track of visited cells
        boolean[][] visited = new boolean[n][m];
        
        // Check if starting position is valid
        if(r < 0 || c < 0 || r >= n || c >= m || mat[r][c] == '#')
            return 0;
        
        // Run DFS from starting position
        dfs(r, c, u, d, mat, visited);
        
        // Return the number of unique cells
        int ans = 0;
        for (int i=0; i<n; i++) {
            for (int j=0; j<m; j++) {
                if (visited[i][j]) ans++;
            }
        }
        
        return ans;
    }

    public static void main(String[] args) {
        char[][] mat = {
            {'.', '.', '.'},
            {'.', '#', '.'},
            {'#', '.', '.'}
        };
        
        int r = 1, c = 0;
        int u = 1, d = 1;
        
        System.out.println(numberOfCells(r, c, u, d, mat));
    }
}
Python
# Python program to solve Geek in a Maze problem

def dfs(r, c, u, d, mat, visited):
    n, m = len(mat), len(mat[0])
    
    # If out of bounds or obstacle or already visited, return
    if r < 0 or c < 0 or r >= n or c >= m or mat[r][c] == '#':
        return
    
    # Mark the cell as visited
    visited[r][c] = True
    mat[r][c] = '#'
    
    # Explore in all four directions
    # Up
    if u > 0:
        dfs(r-1, c, u-1, d, mat, visited)
    
    # Down
    if d > 0:
        dfs(r+1, c, u, d-1, mat, visited)
    
    # Left
    dfs(r, c-1, u, d, mat, visited)
    
    # Right
    dfs(r, c+1, u, d, mat, visited)
    
    mat[r][c] = '.'

def numberOfCells(r, c, u, d, mat):
    n, m = len(mat), len(mat[0])
    
    # Create a visited array to keep track of visited cells
    visited = [[False] * m for _ in range(n)]
    
    # Check if starting position is valid
    if r < 0 or c < 0 or r >= n or c >= m or mat[r][c] == '#':
        return 0
    
    # Run DFS from starting position
    dfs(r, c, u, d, mat, visited)
    
    # Return the number of unique cells
    return sum(sum(row) for row in visited)

if __name__ == "__main__":
    mat = [
        ['.', '.', '.'],
        ['.', '#', '.'],
        ['#', '.', '.']
    ]
    
    r, c = 1, 0
    u, d = 1, 1
    
    print(numberOfCells(r, c, u, d, mat))
C#
// C# program to solve Geek in a Maze problem
using System;

class GfG {
    
    static void dfs(int r, int c, int u, int d, char[,] mat, bool[,] visited) {
        int n = mat.GetLength(0), m = mat.GetLength(1);
        
        // If out of bounds or obstacle or already visited, return
        if (r < 0 || c < 0 || r >= n || c >= m || mat[r, c] == '#')
            return;
        
        // Mark the cell as visited
        visited[r, c] = true;
        mat[r, c] = '#';
        
        // Explore in all four directions
        // Up
        if (u > 0)
            dfs(r-1, c, u-1, d, mat, visited);
        
        // Down
        if (d > 0)
            dfs(r+1, c, u, d-1, mat, visited);
        
        // Left
        dfs(r, c-1, u, d, mat, visited);
        
        // Right
        dfs(r, c+1, u, d, mat, visited);
        
        mat[r, c] = '.';
    }

    static int numberOfCells(int r, int c, int u, int d, char[,] mat) {
        int n = mat.GetLength(0), m = mat.GetLength(1);
        
        // Create a visited array to keep track of visited cells
        bool[,] visited = new bool[n, m];
        
        // Check if starting position is valid
        if (r < 0 || c < 0 || r >= n || c >= m || mat[r, c] == '#')
            return 0;
        
        // Run DFS from starting position
        dfs(r, c, u, d, mat, visited);
        
        // Return the number of unique cells
        int ans = 0;
        for (int i = 0; i < n; i++) {
            for (int j = 0; j < m; j++) {
                if (visited[i, j]) ans++;
            }
        }
        
        return ans;
    }

    static void Main() {
        char[,] mat = {
            {'.', '.', '.'},
            {'.', '#', '.'},
            {'#', '.', '.'}
        };
        
        int r = 1, c = 0;
        int u = 1, d = 1;
        
        Console.WriteLine(numberOfCells(r, c, u, d, mat));
    }
}
JavaScript
// JavaScript program to solve Geek in a Maze problem

function dfs(r, c, u, d, mat, visited) {
    let n = mat.length, m = mat[0].length;

    // If out of bounds or obstacle or already visited, return
    if (r < 0 || c < 0 || r >= n || c >= m || mat[r][c] === '#') 
        return;
    
    // Mark the cell as visited
    visited[r][c] = true;
    mat[r][c] = '#';
    
    // Explore in all four directions
    // Up
    if (u > 0) 
        dfs(r - 1, c, u - 1, d, mat, visited);
    
    // Down
    if (d > 0) 
        dfs(r + 1, c, u, d - 1, mat, visited);
    
    // Left
    dfs(r, c - 1, u, d, mat, visited);
    
    // Right
    dfs(r, c + 1, u, d, mat, visited);
    
    mat[r][c] = '.';
}

function numberOfCells(r, c, u, d, mat) {
    let n = mat.length, m = mat[0].length;
    
    // Create a visited array to keep track of visited cells
    let visited = Array.from({ length: n }, () => Array(m).fill(false));
    
    // Check if starting position is valid
    if (r < 0 || c < 0 || r >= n || c >= m || mat[r][c] === '#') 
        return 0;
    
    // Run DFS from starting position
    dfs(r, c, u, d, mat, visited);
    
    return visited.flat().filter(Boolean).length;
}

let mat = [['.', '.', '.'], ['.', '#', '.'], ['#', '.', '.']];
console.log(numberOfCells(1, 0, 1, 1, mat));

Output
5

Time Complexity : O(4^(n*m)) since we are making 4 calls for n*m items in a matrix
Auxiliary Space : O(1) since we are using the same matrix as visited matrix

[Expected Approach] Using Priority Queue

The idea is to use a modified version of Dijkstra's algorithm with a priority queue to explore all reachable cells in the maze while following the constraints on upward and downward movements. By keeping track of the number of up and down moves used to reach each cell and marking cells as visited only when all constraints are satisfied, we can efficiently determine the total count of unique cells that Geek can reach from his starting position.

Step by step approach:

  1. Check if the starting position is an obstacle - if yes, return 0.
  2. Use a priority queue to store states as vectors [up moves, down moves, row, col]. Initialize a 2D visited array to track cells we've already reached.
  3. Start BFS traversal from the given position (r, c)
  4. For each position, explore four possible directions (up, down, left, right):
    • When moving up, increment the up moves counter and check if it's still â‰Ī u.
    • When moving down, increment the down moves counter and check if it's still â‰Ī d.
    • For horizontal movements, no counters need to be incremented.
  5. Mark each valid cell as visited and add its state to the queue.
  6. After exploration is complete, count the total number of cells marked as visited.
C++
// C++ program to solve Geek in a Maze problem
#include <bits/stdc++.h>
using namespace std;

// Function to check if a cell 
// is valid or not.
bool isValid(int row, int col, int n, int m) {
    if(row >= 0 && row < n && col >= 0 && col < m)
        return true;

    return false;
}

//Function to find the number of valid cells
int numberOfCells(int r, int c, int u, int d, vector<vector<char>> &mat) {
    int n = mat.size(), m = mat[0].size();
    
    //If the starting cell is a 
    // blocked cell, return 0
    if(mat[r][c] == '#')
        return 0;
    
    //Each vector contains [up moves, down moves, row, col]
    priority_queue<vector<int>, vector<vector<int>>, 
    greater<vector<int>>> pq;
    
    //Matrix to keep track of visited cells
    vector<vector<int>> vis(n, vector<int>(m, 0));
    
    pq.push({0, 0, r, c});
    vis[r][c] = 1;    

    while(!pq.empty()) {
        vector<int> current = pq.top();
        int up = current[0];
        int down = current[1];
        int x = current[2];
        int y = current[3];

        pq.pop();

        //Checking the adjacent cells with combined if statements
        //Up direction
        if(isValid(x - 1, y, n, m) && up + 1 <= u && 
        !vis[x - 1][y] && mat[x - 1][y] == '.') {
            pq.push({up + 1, down, x - 1, y});    
            vis[x - 1][y] = 1;    
        }

        //Down direction
        if(isValid(x + 1, y, n, m) && down + 1 <= d && 
        !vis[x + 1][y] && mat[x + 1][y] == '.') {
            pq.push({up, down + 1, x + 1, y});    
            vis[x + 1][y] = 1;    
        }

        //Left direction
        if(isValid(x, y - 1, n, m) && !vis[x][y - 1] && 
        mat[x][y - 1] == '.') {
            pq.push({up, down, x, y - 1});    
            vis[x][y - 1] = 1;    
        }

        //Right direction
        if(isValid(x, y + 1, n, m) && !vis[x][y + 1] && 
        mat[x][y + 1] == '.') {
            pq.push({up, down, x, y + 1});
            vis[x][y + 1] = 1;    
        }
    }
    
    //Counting the number of visited cells
    int ans = 0;

    for(int i = 0; i < n; i++) {
        for(int j = 0; j < m; j++) {
            if(vis[i][j] == 1) {
                ans++;
            }
        }
    }

    //Returning the number of valid cells
    return ans;
}

int main() {
    vector<vector<char>> mat = 
      {{'.', '.', '.'},
       {'.', '#', '.'},
       {'#', '.', '.'}};
       
    int r = 1, c = 0;
    int u = 1, d = 1;
    
    cout << numberOfCells(r, c, u, d, mat);
    
    return 0;
}
Java
// Java program to solve Geek in a Maze problem
import java.util.PriorityQueue;

class GfG {
    
    // Function to check if a cell 
    // is valid or not.
    static boolean isValid(int row, int col, int n, int m) {
        if(row >= 0 && row < n && col >= 0 && col < m)
            return true;
        return false;
    }

    // Function to find the number of valid cells
    static int numberOfCells(int r, int c, int u, int d, char[][] mat) {
        int n = mat.length, m = mat[0].length;
        
        // If the starting cell is a 
        // blocked cell, return 0
        if(mat[r][c] == '#')
            return 0;
        
        // Each array contains [up moves, down moves, row, col]
        PriorityQueue<int[]> pq = new PriorityQueue<>((a, b) -> {
            if(a[0] != b[0]) return a[0] - b[0];
            return a[1] - b[1];
        });

        // Matrix to keep track of visited cells
        int[][] vis = new int[n][m];

        pq.add(new int[]{0, 0, r, c});
        vis[r][c] = 1;

        while(!pq.isEmpty()) {
            int[] current = pq.poll();
            int up = current[0];
            int down = current[1];
            int x = current[2];
            int y = current[3];

            // Up direction
            if(isValid(x - 1, y, n, m) && up + 1 <= u && 
            vis[x - 1][y] == 0 && mat[x - 1][y] == '.') {
                pq.add(new int[]{up + 1, down, x - 1, y});
                vis[x - 1][y] = 1;
            }

            // Down direction
            if(isValid(x + 1, y, n, m) && down + 1 <= d && 
            vis[x + 1][y] == 0 && mat[x + 1][y] == '.') {
                pq.add(new int[]{up, down + 1, x + 1, y});
                vis[x + 1][y] = 1;
            }

            // Left direction
            if(isValid(x, y - 1, n, m) && vis[x][y - 1] == 0 && 
            mat[x][y - 1] == '.') {
                pq.add(new int[]{up, down, x, y - 1});
                vis[x][y - 1] = 1;
            }

            // Right direction
            if(isValid(x, y + 1, n, m) && vis[x][y + 1] == 0 && 
            mat[x][y + 1] == '.') {
                pq.add(new int[]{up, down, x, y + 1});
                vis[x][y + 1] = 1;
            }
        }

        // Counting the number of visited cells
        int ans = 0;
        for(int i = 0; i < n; i++) {
            for(int j = 0; j < m; j++) {
                if(vis[i][j] == 1) {
                    ans++;
                }
            }
        }

        // Returning the number of valid cells
        return ans;
    }

    public static void main(String[] args) {
        char[][] mat = {
            {'.', '.', '.'},
            {'.', '#', '.'},
            {'#', '.', '.'}
        };

        int r = 1, c = 0;
        int u = 1, d = 1;

        System.out.println(numberOfCells(r, c, u, d, mat));
    }
}
Python
# Python program to solve Geek in a Maze problem
import heapq

# Function to check if a cell 
# is valid or not.
def isValid(row, col, n, m):
    if 0 <= row < n and 0 <= col < m:
        return True
    return False

# Function to find the number of valid cells
def numberOfCells(r, c, u, d, mat):
    n, m = len(mat), len(mat[0])
    
    # If the starting cell is a 
    # blocked cell, return 0
    if mat[r][c] == '#':
        return 0
    
    # Each list contains [up moves, down moves, row, col]
    pq = []
    heapq.heappush(pq, (0, 0, r, c))

    # Matrix to keep track of visited cells
    vis = [[0] * m for _ in range(n)]
    vis[r][c] = 1

    while pq:
        up, down, x, y = heapq.heappop(pq)

        # Up direction
        if isValid(x - 1, y, n, m) and up + 1 <= u and \
        not vis[x - 1][y] and mat[x - 1][y] == '.':
            heapq.heappush(pq, (up + 1, down, x - 1, y))
            vis[x - 1][y] = 1

        # Down direction
        if isValid(x + 1, y, n, m) and down + 1 <= d and \
        not vis[x + 1][y] and mat[x + 1][y] == '.':
            heapq.heappush(pq, (up, down + 1, x + 1, y))
            vis[x + 1][y] = 1

        # Left direction
        if isValid(x, y - 1, n, m) and not vis[x][y - 1] and \
        mat[x][y - 1] == '.':
            heapq.heappush(pq, (up, down, x, y - 1))
            vis[x][y - 1] = 1

        # Right direction
        if isValid(x, y + 1, n, m) and not vis[x][y + 1] and \
        mat[x][y + 1] == '.':
            heapq.heappush(pq, (up, down, x, y + 1))
            vis[x][y + 1] = 1

    # Counting the number of visited cells
    ans = sum(row.count(1) for row in vis)

    # Returning the number of valid cells
    return ans

if __name__ == "__main__":
    mat = [
        ['.', '.', '.'],
        ['.', '#', '.'],
        ['#', '.', '.']
    ]

    r, c = 1, 0
    u, d = 1, 1

    print(numberOfCells(r, c, u, d, mat))
C#
// C# program to solve Geek in a Maze problem
using System;
using System.Collections.Generic;

// Custom comparator class for min heap
class Comparer : IComparer<int[]> {
    public int Compare(int[] a, int[] b) {
        if (a[0] != b[0]) {
            if (a[0] > b[0]) return 1;
            else return 0;
        }
        else if (a[1] != b[1]) {
            if (a[1] > b[1]) return 1;
            else return 0;
        }
        return 0;
    }
}

class GfG {
    
    // Function to check if a cell 
    // is valid or not.
    static bool isValid(int row, int col, int n, int m) {
        if(row >= 0 && row < n && col >= 0 && col < m)
            return true;

        return false;
    }

    // Function to find the number of valid cells
    static int numberOfCells(int r, int c, int u, int d, char[][] mat) {
        int n = mat.Length, m = mat[0].Length;
        
        // If the starting cell is a 
        // blocked cell, return 0
        if(mat[r][c] == '#')
            return 0;
        
        PriorityQueue<int[]> pq = new PriorityQueue<int[]>(new Comparer());
        
        // Matrix to keep track of visited cells
        int[][] vis = new int[n][];
        for(int i = 0; i < n; i++)
            vis[i] = new int[m];

        pq.Enqueue(new int[] {0, 0, r, c});
        vis[r][c] = 1;    

        while(pq.Count > 0) {
            int[] current = pq.Dequeue();
            int up = current[0];
            int down = current[1];
            int x = current[2];
            int y = current[3];

            // Checking the adjacent cells with combined if statements
            // Up direction
            if(isValid(x - 1, y, n, m) && up + 1 <= u && 
            vis[x - 1][y] == 0 && mat[x - 1][y] == '.') {
                pq.Enqueue(new int[] {up + 1, down, x - 1, y});    
                vis[x - 1][y] = 1;    
            }

            // Down direction
            if(isValid(x + 1, y, n, m) && down + 1 <= d && 
            vis[x + 1][y] == 0 && mat[x + 1][y] == '.') {
                pq.Enqueue(new int[] {up, down + 1, x + 1, y});    
                vis[x + 1][y] = 1;    
            }

            // Left direction
            if(isValid(x, y - 1, n, m) && vis[x][y - 1] == 0 && 
            mat[x][y - 1] == '.') {
                pq.Enqueue(new int[] {up, down, x, y - 1});    
                vis[x][y - 1] = 1;    
            }

            // Right direction
            if(isValid(x, y + 1, n, m) && vis[x][y + 1] == 0 && 
            mat[x][y + 1] == '.') {
                pq.Enqueue(new int[] {up, down, x, y + 1});
                vis[x][y + 1] = 1;    
            }
        }
        
        // Counting the number of visited cells
        int ans = 0;

        for(int i = 0; i < n; i++) {
            for(int j = 0; j < m; j++) {
                if(vis[i][j] == 1) {
                    ans++;
                }
            }
        }

        // Returning the number of valid cells
        return ans;
    }

    static void Main() {
        char[][] mat = {
            new char[] {'.', '.', '.'},
            new char[] {'.', '#', '.'},
            new char[] {'#', '.', '.'}
        };
       
        int r = 1, c = 0;
        int u = 1, d = 1;
    
        Console.WriteLine(numberOfCells(r, c, u, d, mat));
    }
}

// Custom Priority queue 
class PriorityQueue<T> {
    private List<T> heap;
    private IComparer<T> comparer;

    public PriorityQueue(IComparer<T> comparer = null) {
        this.heap = new List<T>();
        this.comparer = comparer ?? Comparer<T>.Default;
    }

    public int Count => heap.Count;

    // Enqueue operation
    public void Enqueue(T item) {
        heap.Add(item);
        int i = heap.Count - 1;
        while (i > 0) {
            int parent = (i - 1) / 2;
            if (comparer.Compare(heap[parent], heap[i]) <= 0)
                break;
            Swap(parent, i);
            i = parent;
        }
    }

    // Dequeue operation
    public T Dequeue() {
        if (heap.Count == 0)
            throw new InvalidOperationException("Priority queue is empty.");
        T result = heap[0];
        int last = heap.Count - 1;
        heap[0] = heap[last];
        heap.RemoveAt(last);
        last--;
        int i = 0;
        while (true) {
            int left = 2 * i + 1;
            if (left > last)
                break;
            int right = left + 1;
            int minChild = left;
            if (right <= last && comparer.Compare(heap[right], heap[left]) < 0)
                minChild = right;
            if (comparer.Compare(heap[i], heap[minChild]) <= 0)
                break;
            Swap(i, minChild);
            i = minChild;
        }
        return result;
    }

    // Swap two elements in the heap
    private void Swap(int i, int j) {
        T temp = heap[i];
        heap[i] = heap[j];
        heap[j] = temp;
    }
}
JavaScript
// JavaScript program to solve Geek in a Maze problem

// Comparator function to compare Node data
function nodeComparator(k1, k2) {
	if (a[0] != b[0]) {
	    if (a[0] > b[0]) return -1;
	    else return 1;
	}
	else if (a[1] != b[1]) {
	    if (a[1] > b[1]) return -1;
	    else return 1;
	}
    else return 0;
}

class PriorityQueue {
	constructor(compare) {
		this.heap = [];
		this.compare = compare;
	}

	enqueue(value) {
		this.heap.push(value);
		this.bubbleUp();
	}

	bubbleUp() {
		let index = this.heap.length - 1;
		while (index > 0) {
			let element = this.heap[index],
			    parentIndex = Math.floor((index - 1) / 2),
			    parent = this.heap[parentIndex];
			if (this.compare(element, parent) < 0) break;
			this.heap[index] = parent;
			this.heap[parentIndex] = element;
			index = parentIndex;
		}
	}

	dequeue() {
		let max = this.heap[0];
		let end = this.heap.pop();
		if (this.heap.length > 0) {
			this.heap[0] = end;
			this.sinkDown(0);
		}
		return max;
	}

	sinkDown(index) {
		let left = 2 * index + 1,
		    right = 2 * index + 2,
		    largest = index;

		if (
		    left < this.heap.length &&
		    this.compare(this.heap[left], this.heap[largest]) > 0
		) {
			largest = left;
		}

		if (
		    right < this.heap.length &&
		    this.compare(this.heap[right], this.heap[largest]) > 0
		) {
			largest = right;
		}

		if (largest !== index) {
			[this.heap[largest], this.heap[index]] = [
			            this.heap[index],
			            this.heap[largest],
			        ];
			this.sinkDown(largest);
		}
	}

	isEmpty() {
		return this.heap.length === 0;
	}
}

// Function to check if a cell
// is valid or not.
function isValid(row, col, n, m) {
	return row >= 0 && row < n && col >= 0 && col < m;
}

// Function to find the number of valid cells
function numberOfCells(r, c, u, d, mat) {
	let n = mat.length, m = mat[0].length;

	// If the starting cell is a
	// blocked cell, return 0
	if (mat[r][c] === '#') return 0;

	let pq = new PriorityQueue((a, b) => a[0] - b[0]);

	// Matrix to keep track of visited cells
	let vis = Array.from({ length: n }, () => Array(m).fill(0));

	pq.enqueue([0, 0, r, c]);
	vis[r][c] = 1;

	while (!pq.isEmpty()) {
		let [up, down, x, y] = pq.dequeue();

		// Checking the adjacent cells with combined if statements
		// Up direction
		if (isValid(x - 1, y, n, m) && up + 1 <= u &&
		        vis[x - 1][y] === 0 && mat[x - 1][y] === '.') {
			pq.enqueue([up + 1, down, x - 1, y]);
			vis[x - 1][y] = 1;
		}

		// Down direction
		if (isValid(x + 1, y, n, m) && down + 1 <= d &&
		        vis[x + 1][y] === 0 && mat[x + 1][y] === '.') {
			pq.enqueue([up, down + 1, x + 1, y]);
			vis[x + 1][y] = 1;
		}

		// Left direction
		if (isValid(x, y - 1, n, m) && vis[x][y - 1] === 0 &&
		        mat[x][y - 1] === '.') {
			pq.enqueue([up, down, x, y - 1]);
			vis[x][y - 1] = 1;
		}

		// Right direction
		if (isValid(x, y + 1, n, m) && vis[x][y + 1] === 0 &&
		        mat[x][y + 1] === '.') {
			pq.enqueue([up, down, x, y + 1]);
			vis[x][y + 1] = 1;
		}
	}

	// Counting the number of visited cells
	let ans = 0;

	for (let i = 0; i < n; i++) {
		for (let j = 0; j < m; j++) {
			if (vis[i][j] === 1) {
				ans++;
			}
		}
	}

	// Returning the number of valid cells
	return ans;
}

let mat = [
              ['.', '.', '.'],
              ['.', '#', '.'],
              ['#', '.', '.']
           ];

let r = 1, c = 0;
let u = 1, d = 1;

console.log(numberOfCells(r, c, u, d, mat));

Output
5

Time Complexity: O(n * m) where n is the number of rows and m is the number of columns in the maze. In the worst case, we might need to visit each cell in the maze.
Auxiliary Space: O(n * m). The priority queue can store up to n × m states in the worst case.

Comment