Find number of closed islands in given Matrix
Last Updated :
15 Jul, 2025
Given a binary matrix mat[][] of dimensions NxM such that 1 denotes the island and 0 denotes the water. The task is to find the number of closed islands in the given matrix.
A closed island is known as the group of 1s that is surrounded by only 0s on all the four sides (excluding diagonals). If any 1 is at the edges of the given matrix then it is not considered as the part of the connected island as it is not surrounded by all 0.
Examples:
Input: N = 5, M = 8,
mat[][] =
{{0, 0, 0, 0, 0, 0, 0, 1},
{0, 1, 1, 1, 1, 0, 0, 1},
{0, 1, 0, 1, 0, 0, 0, 1},
{0, 1, 1, 1, 1, 0, 1, 0},
{0, 0, 0, 0, 0, 0, 0, 1}}
Output: 2
Explanation:
mat[][] =
{{0, 0, 0, 0, 0, 0, 0, 1},
{0, 1, 1, 1, 1, 0, 0, 1},
{0, 1, 0, 1, 0, 0, 0, 1},
{0, 1, 1, 1, 1, 0, 1, 0},
{0, 0, 0, 0, 0, 0, 0, 1}}
There are 2 closed islands.
The islands in dark are closed because they are completely surrounded by
0s (water).
There are two more islands in the last column of the matrix, but they are not completely surrounded by 0s.
Hence they are not closed islands.
Input: N = 3, M = 3, matrix[][] =
{{1, 0, 0},
{0, 1, 0},
{0, 0, 1}}
Output: 1
Method 1 - using DFS Traversal: The idea is to use DFS Traversal to count the number of island surrounded by water. But we have to keep the track of the island at the corner of the given matrix as they will not be counted in the resultant island. Below are the steps:
- Initialize a 2D visited matrix(say vis[][]) to keep the track of traversed cell in the given matrix.
- Perform DFS Traversal on all the corner of the given matrix and if any element has value 1 then marked all the cell with value 1 as visited because it cannot be counted in the resultant count.
- Perform DFS Traversal on all the remaining unvisited cell and if value encountered is 1 then marked this cell as visited, count this island in the resultant count and recursively call DFS for all the 4 directions i.e., left, right, top, and bottom to make all the 1s connected to the current cell as visited.
- Repeat the above step until all cell with value 1 are not visited.
Below is the implementation of the above approach:
C++
// C++ program for the above approach
#include <bits/stdc++.h>
using namespace std;
// DFS Traversal to find the count of
// island surrounded by water
void dfs(vector<vector<int> >& matrix,
vector<vector<bool> >& visited, int x, int y,
int n, int m)
{
// If the land is already visited
// or there is no land or the
// coordinates gone out of matrix
// break function as there
// will be no islands
if (x < 0 || y < 0 || x >= n || y >= m
|| visited[x][y] == true || matrix[x][y] == 0)
return;
// Mark land as visited
visited[x][y] = true;
// Traverse to all adjacent elements
dfs(matrix, visited, x + 1, y, n, m);
dfs(matrix, visited, x, y + 1, n, m);
dfs(matrix, visited, x - 1, y, n, m);
dfs(matrix, visited, x, y - 1, n, m);
}
// Function that counts the closed island
int countClosedIsland(vector<vector<int> >& matrix, int n,
int m)
{
// Create boolean 2D visited matrix
// to keep track of visited cell
// Initially all elements are
// unvisited.
vector<vector<bool> > visited(n,
vector<bool>(m, false));
// Mark visited all lands
// that are reachable from edge
for (int i = 0; i < n; ++i) {
for (int j = 0; j < m; ++j) {
// Traverse corners
if ((i * j == 0 || i == n - 1 || j == m - 1)
and matrix[i][j] == 1
and visited[i][j] == false)
dfs(matrix, visited, i, j, n, m);
}
}
// To stores number of closed islands
int result = 0;
for (int i = 0; i < n; ++i) {
for (int j = 0; j < m; ++j) {
// If the land not visited
// then there will be atleast
// one closed island
if (visited[i][j] == false
and matrix[i][j] == 1) {
result++;
// Mark all lands associated
// with island visited.
dfs(matrix, visited, i, j, n, m);
}
}
}
// Return the final count
return result;
}
// Driver Code
int main()
{
// Given size of Matrix
int N = 5, M = 8;
// Given Matrix
vector<vector<int> > matrix
= { { 0, 0, 0, 0, 0, 0, 0, 1 },
{ 0, 1, 1, 1, 1, 0, 0, 1 },
{ 0, 1, 0, 1, 0, 0, 0, 1 },
{ 0, 1, 1, 1, 1, 0, 1, 0 },
{ 0, 0, 0, 0, 0, 0, 0, 1 } };
// Function Call
cout << countClosedIsland(matrix, N, M);
return 0;
}
Java
// Java program for the above approach
import java.util.*;
class GFG {
// DFS Traversal to find the count of
// island surrounded by water
static void dfs(int[][] matrix, boolean[][] visited,
int x, int y, int n, int m)
{
// If the land is already visited
// or there is no land or the
// coordinates gone out of matrix
// break function as there
// will be no islands
if (x < 0 || y < 0 || x >= n || y >= m
|| visited[x][y] == true || matrix[x][y] == 0)
return;
// Mark land as visited
visited[x][y] = true;
// Traverse to all adjacent elements
dfs(matrix, visited, x + 1, y, n, m);
dfs(matrix, visited, x, y + 1, n, m);
dfs(matrix, visited, x - 1, y, n, m);
dfs(matrix, visited, x, y - 1, n, m);
}
// Function that counts the closed island
static int countClosedIsland(int[][] matrix, int n,
int m)
{
// Create boolean 2D visited matrix
// to keep track of visited cell
// Initially all elements are
// unvisited.
boolean[][] visited = new boolean[n][m];
// Mark visited all lands
// that are reachable from edge
for (int i = 0; i < n; ++i) {
for (int j = 0; j < m; ++j) {
// Traverse corners
if ((i * j == 0 || i == n - 1 || j == m - 1)
&& matrix[i][j] == 1
&& visited[i][j] == false)
dfs(matrix, visited, i, j, n, m);
}
}
// To stores number of closed islands
int result = 0;
for (int i = 0; i < n; ++i) {
for (int j = 0; j < m; ++j) {
// If the land not visited
// then there will be atleast
// one closed island
if (visited[i][j] == false
&& matrix[i][j] == 1) {
result++;
// Mark all lands associated
// with island visited.
dfs(matrix, visited, i, j, n, m);
}
}
}
// Return the final count
return result;
}
// Driver Code
public static void main(String[] args)
{
// Given size of Matrix
int N = 5, M = 8;
// Given Matrix
int[][] matrix = { { 0, 0, 0, 0, 0, 0, 0, 1 },
{ 0, 1, 1, 1, 1, 0, 0, 1 },
{ 0, 1, 0, 1, 0, 0, 0, 1 },
{ 0, 1, 1, 1, 1, 0, 1, 0 },
{ 0, 0, 0, 0, 0, 0, 0, 1 } };
// Function Call
System.out.print(countClosedIsland(matrix, N, M));
}
}
// This code is contributed by Rohit_ranjan
Python
# Python3 program for the above approach
# DFS Traversal to find the count of
# island surrounded by water
def dfs(matrix, visited, x, y, n, m):
# If the land is already visited
# or there is no land or the
# coordinates gone out of matrix
# break function as there
# will be no islands
if (x < 0 or y < 0 or
x >= n or y >= m or
visited[x][y] == True or
matrix[x][y] == 0):
return
# Mark land as visited
visited[x][y] = True
# Traverse to all adjacent elements
dfs(matrix, visited, x + 1, y, n, m);
dfs(matrix, visited, x, y + 1, n, m);
dfs(matrix, visited, x - 1, y, n, m);
dfs(matrix, visited, x, y - 1, n, m);
# Function that counts the closed island
def countClosedIsland(matrix, n, m):
# Create boolean 2D visited matrix
# to keep track of visited cell
# Initially all elements are
# unvisited.
visited = [[False for i in range(m)]
for j in range(n)]
# Mark visited all lands
# that are reachable from edge
for i in range(n):
for j in range(m):
# Traverse corners
if ((i * j == 0 or i == n - 1 or
j == m - 1) and matrix[i][j] == 1 and
visited[i][j] == False):
dfs(matrix, visited, i, j, n, m)
# To stores number of closed islands
result = 0
for i in range(n):
for j in range(m):
# If the land not visited
# then there will be atleast
# one closed island
if (visited[i][j] == False and
matrix[i][j] == 1):
result += 1
# Mark all lands associated
# with island visited.
dfs(matrix, visited, i, j, n, m)
# Return the final count
return result
# Driver Code
# Given size of Matrix
N = 5
M = 8
# Given Matrix
matrix = [ [ 0, 0, 0, 0, 0, 0, 0, 1 ],
[ 0, 1, 1, 1, 1, 0, 0, 1 ],
[ 0, 1, 0, 1, 0, 0, 0, 1 ],
[ 0, 1, 1, 1, 1, 0, 1, 0 ],
[ 0, 0, 0, 0, 0, 0, 0, 1 ] ]
# Function Call
print(countClosedIsland(matrix, N, M))
# This code is contributed by rag2127
C#
// C# program for the above approach
using System;
class GFG {
// DFS Traversal to find the count of
// island surrounded by water
static void dfs(int[, ] matrix, bool[, ] visited, int x,
int y, int n, int m)
{
// If the land is already visited
// or there is no land or the
// coordinates gone out of matrix
// break function as there
// will be no islands
if (x < 0 || y < 0 || x >= n || y >= m
|| visited[x, y] == true || matrix[x, y] == 0)
return;
// Mark land as visited
visited[x, y] = true;
// Traverse to all adjacent elements
dfs(matrix, visited, x + 1, y, n, m);
dfs(matrix, visited, x, y + 1, n, m);
dfs(matrix, visited, x - 1, y, n, m);
dfs(matrix, visited, x, y - 1, n, m);
}
// Function that counts the closed island
static int countClosedIsland(int[, ] matrix, int n,
int m)
{
// Create bool 2D visited matrix
// to keep track of visited cell
// Initially all elements are
// unvisited.
bool[, ] visited = new bool[n, m];
// Mark visited all lands
// that are reachable from edge
for (int i = 0; i < n; ++i) {
for (int j = 0; j < m; ++j) {
// Traverse corners
if ((i * j == 0 || i == n - 1 || j == m - 1)
&& matrix[i, j] == 1
&& visited[i, j] == false)
dfs(matrix, visited, i, j, n, m);
}
}
// To stores number of closed islands
int result = 0;
for (int i = 0; i < n; ++i) {
for (int j = 0; j < m; ++j) {
// If the land not visited
// then there will be atleast
// one closed island
if (visited[i, j] == false
&& matrix[i, j] == 1) {
result++;
// Mark all lands associated
// with island visited.
dfs(matrix, visited, i, j, n, m);
}
}
}
// Return the readonly count
return result;
}
// Driver Code
public static void Main(String[] args)
{
// Given size of Matrix
int N = 5, M = 8;
// Given Matrix
int[, ] matrix = { { 0, 0, 0, 0, 0, 0, 0, 1 },
{ 0, 1, 1, 1, 1, 0, 0, 1 },
{ 0, 1, 0, 1, 0, 0, 0, 1 },
{ 0, 1, 1, 1, 1, 0, 1, 0 },
{ 0, 0, 0, 0, 0, 0, 0, 1 } };
// Function call
Console.Write(countClosedIsland(matrix, N, M));
}
}
// This code is contributed by amal kumar choubey
JavaScript
<script>
// JavaScript program for the above approach
// DFS Traversal to find the count of
// island surrounded by water
function dfs(matrix, visited, x, y, n, m)
{
// If the land is already visited
// or there is no land or the
// coordinates gone out of matrix
// break function as there
// will be no islands
if (x < 0 || y < 0 || x >= n || y >= m
|| visited[x][y] == true || matrix[x][y] == 0)
return;
// Mark land as visited
visited[x][y] = true;
// Traverse to all adjacent elements
dfs(matrix, visited, x + 1, y, n, m);
dfs(matrix, visited, x, y + 1, n, m);
dfs(matrix, visited, x - 1, y, n, m);
dfs(matrix, visited, x, y - 1, n, m);
}
// Function that counts the closed island
function countClosedIsland(matrix, n, m)
{
// Create boolean 2D visited matrix
// to keep track of visited cell
// Initially all elements are
// unvisited.
let visited = new Array(n);
for (let i = 0; i < n; ++i)
{
visited[i] = new Array(m);
for (let j = 0; j < m; ++j)
{
visited[i][j] = false;
}
}
// Mark visited all lands
// that are reachable from edge
for (let i = 0; i < n; ++i) {
for (let j = 0; j < m; ++j) {
// Traverse corners
if ((i * j == 0 || i == n - 1 || j == m - 1)
&& matrix[i][j] == 1
&& visited[i][j] == false)
dfs(matrix, visited, i, j, n, m);
}
}
// To stores number of closed islands
let result = 0;
for (let i = 0; i < n; ++i) {
for (let j = 0; j < m; ++j) {
// If the land not visited
// then there will be atleast
// one closed island
if (visited[i][j] == false
&& matrix[i][j] == 1) {
result++;
// Mark all lands associated
// with island visited.
dfs(matrix, visited, i, j, n, m);
}
}
}
// Return the final count
return result;
}
// Given size of Matrix
let N = 5, M = 8;
// Given Matrix
let matrix = [ [ 0, 0, 0, 0, 0, 0, 0, 1 ],
[ 0, 1, 1, 1, 1, 0, 0, 1 ],
[ 0, 1, 0, 1, 0, 0, 0, 1 ],
[ 0, 1, 1, 1, 1, 0, 1, 0 ],
[ 0, 0, 0, 0, 0, 0, 0, 1 ] ];
// Function Call
document.write(countClosedIsland(matrix, N, M));
</script>
Time Complexity: O(N*M)
Auxiliary Space: O(N*M)
Method: Single DFS Traversal
Improvement over Method 1: In the above Method 1, we see that we are calling DFS traversal twice (Once over the corner cells with '1' and afterward over the cells which are not on the corners with '1' and are not visited). We can solve this using only 1 DFS traversal. the idea is to call DFS for the cells with value '1' which are not on the corners and while doing so, if we find a cell with value '1' on the corner, then that means it should not be counted as an island. The code is shown below:
C++
// C++ program for the above approach
#include <bits/stdc++.h>
using namespace std;
// DFS Traversal to find the count of
// island surrounded by water
void dfs(vector<vector<int> >& matrix,
vector<vector<bool> >& visited, int x, int y,
int n, int m, bool &hasCornerCell)
{
// If the land is already visited
// or there is no land or the
// coordinates gone out of matrix
// break function as there
// will be no islands
if (x < 0 || y < 0 || x >= n || y >= m
|| visited[x][y] == true || matrix[x][y] == 0)
return;
// Check for the corner cell
if(x == 0 || y == 0 || x == n-1 || y == m-1)
{
if(matrix[x][y] == 1)
hasCornerCell = true;
}
// Mark land as visited
visited[x][y] = true;
// Traverse to all adjacent elements
dfs(matrix, visited, x + 1, y, n, m, hasCornerCell);
dfs(matrix, visited, x, y + 1, n, m, hasCornerCell);
dfs(matrix, visited, x - 1, y, n, m, hasCornerCell);
dfs(matrix, visited, x, y - 1, n, m, hasCornerCell);
}
// Function that counts the closed island
int countClosedIsland(vector<vector<int> >& matrix, int n,
int m)
{
// Create boolean 2D visited matrix
// to keep track of visited cell
// Initially all elements are
// unvisited.
vector<vector<bool>> visited(n,vector<bool>(m, false));
// Store the count of islands
int result = 0;
// Call DFS on the cells which
// are not on corners with value '1'
for (int i = 0; i < n; ++i)
{
for (int j = 0; j < m; ++j)
{
if ((i != 0 && j != 0 && i != n - 1 && j != m - 1)
and matrix[i][j] == 1
and visited[i][j] == false)
{
// Determine if the island is closed
bool hasCornerCell = false;
/* hasCornerCell will be
updated to true while DFS traversal
if there is a cell with value
'1' on the corner */
dfs(matrix, visited, i, j, n,
m, hasCornerCell);
/* If the island is closed*/
if(!hasCornerCell)
result = result + 1;
}
}
}
// Return the final count
return result;
}
// Driver Code
int main()
{
// Given size of Matrix
int N = 5, M = 8;
// Given Matrix
vector<vector<int> > matrix
= { { 0, 0, 0, 0, 0, 0, 0, 1 },
{ 0, 1, 1, 1, 1, 0, 0, 1 },
{ 0, 1, 0, 1, 0, 0, 0, 1 },
{ 0, 1, 1, 1, 1, 0, 1, 0 },
{ 0, 0, 0, 0, 0, 0, 0, 1 } };
// Function Call
cout << countClosedIsland(matrix, N, M);
return 0;
}
Java
// Java program for the above approach
import java.util.*;
class GFG{
// DFS Traversal to find the count of
// island surrounded by water
static void dfs(int[][] matrix, boolean[][] visited,
int x, int y, int n, int m,
boolean hasCornerCell)
{
// If the land is already visited
// or there is no land or the
// coordinates gone out of matrix
// break function as there
// will be no islands
if (x < 0 || y < 0 || x >= n || y >= m ||
visited[x][y] == true || matrix[x][y] == 0)
return;
if (x == 0 || y == 0 ||
x == n - 1 || y == m - 1)
{
if (matrix[x][y] == 1)
hasCornerCell = true;
}
// Mark land as visited
visited[x][y] = true;
// Traverse to all adjacent elements
dfs(matrix, visited, x + 1, y, n, m,
hasCornerCell);
dfs(matrix, visited, x, y + 1, n, m,
hasCornerCell);
dfs(matrix, visited, x - 1, y, n, m,
hasCornerCell);
dfs(matrix, visited, x, y - 1, n, m,
hasCornerCell);
}
// Function that counts the closed island
static int countClosedIsland(int[][] matrix, int n,
int m)
{
// Create boolean 2D visited matrix
// to keep track of visited cell
// Initially all elements are
// unvisited.
boolean[][] visited = new boolean[n][m];
int result = 0;
// Mark visited all lands
// that are reachable from edge
for(int i = 0; i < n; ++i)
{
for(int j = 0; j < m; ++j)
{
if ((i != 0 && j != 0 &&
i != n - 1 && j != m - 1) &&
matrix[i][j] == 1 &&
visited[i][j] == false)
{
// Determine if the island is closed
boolean hasCornerCell = false;
// hasCornerCell will be updated to
// true while DFS traversal if there
// is a cell with value '1' on the corner
dfs(matrix, visited, i, j, n, m,
hasCornerCell);
// If the island is closed
if (!hasCornerCell)
result = result + 1;
}
}
}
// Return the final count
return result;
}
// Driver Code
public static void main(String[] args)
{
// Given size of Matrix
int N = 5, M = 8;
// Given Matrix
int[][] matrix = { { 0, 0, 0, 0, 0, 0, 0, 1 },
{ 0, 1, 1, 1, 1, 0, 0, 1 },
{ 0, 1, 0, 1, 0, 0, 0, 1 },
{ 0, 1, 1, 1, 1, 0, 1, 0 },
{ 0, 0, 0, 0, 0, 0, 0, 1 } };
// Function Call
System.out.print(countClosedIsland(matrix, N, M));
}
}
// This code is contributed by grand_master
Python
# Python3 program for the above approach
# DFS Traversal to find the count of
# island surrounded by water
def dfs(matrix, visited, x, y, n, m, hasCornerCell):
# If the land is already visited
# or there is no land or the
# coordinates gone out of matrix
# break function as there
# will be no islands
if (x < 0 or y < 0 or
x >= n or y >= m or
visited[x][y] == True or
matrix[x][y] == 0):
return
if (x == 0 or y == 0 or
x == n - 1 or y == m - 1):
if (matrix[x][y] == 1):
hasCornerCell = True
# Mark land as visited
visited[x][y] = True
# Traverse to all adjacent elements
dfs(matrix, visited, x + 1, y, n, m, hasCornerCell)
dfs(matrix, visited, x, y + 1, n, m, hasCornerCell)
dfs(matrix, visited, x - 1, y, n, m, hasCornerCell)
dfs(matrix, visited, x, y - 1, n, m, hasCornerCell)
# Function that counts the closed island
def countClosedIsland(matrix, n, m):
# Create boolean 2D visited matrix
# to keep track of visited cell
# Initially all elements are
# unvisited.
visited = [[False for i in range(m)]
for j in range(n)]
result = 0
# Mark visited all lands
# that are reachable from edge
for i in range(n):
for j in range(m):
if ((i != 0 and j != 0 and
i != n - 1 and j != m - 1) and
matrix[i][j] == 1 and
visited[i][j] == False):
# Determine if the island is closed
hasCornerCell = False
# hasCornerCell will be updated to
# true while DFS traversal if there
# is a cell with value '1' on the corner
dfs(matrix, visited, i, j,
n, m, hasCornerCell)
# If the island is closed
if (not hasCornerCell):
result = result + 1
# Return the final count
return result
# Driver Code
# Given size of Matrix
N, M = 5, 8
# Given Matrix
matrix = [ [ 0, 0, 0, 0, 0, 0, 0, 1 ],
[ 0, 1, 1, 1, 1, 0, 0, 1 ],
[ 0, 1, 0, 1, 0, 0, 0, 1 ],
[ 0, 1, 1, 1, 1, 0, 1, 0 ],
[ 0, 0, 0, 0, 0, 0, 0, 1 ] ]
# Function Call
print(countClosedIsland(matrix, N, M))
# This code is contributed by divyeshrabadiya07
C#
// C# program for the above approach
using System;
class GFG
{
// DFS Traversal to find the count of
// island surrounded by water
static void dfs(int[,] matrix, bool[,] visited,
int x, int y, int n, int m,
bool hasCornerCell)
{
// If the land is already visited
// or there is no land or the
// coordinates gone out of matrix
// break function as there
// will be no islands
if (x < 0 || y < 0 || x >= n || y >= m ||
visited[x, y] == true || matrix[x, y] == 0)
return;
if (x == 0 || y == 0 ||
x == n - 1 || y == m - 1)
{
if (matrix[x, y] == 1)
hasCornerCell = true;
}
// Mark land as visited
visited[x, y] = true;
// Traverse to all adjacent elements
dfs(matrix, visited, x + 1, y, n, m,
hasCornerCell);
dfs(matrix, visited, x, y + 1, n, m,
hasCornerCell);
dfs(matrix, visited, x - 1, y, n, m,
hasCornerCell);
dfs(matrix, visited, x, y - 1, n, m,
hasCornerCell);
}
// Function that counts the closed island
static int countClosedIsland(int[,] matrix, int n,
int m)
{
// Create boolean 2D visited matrix
// to keep track of visited cell
// Initially all elements are
// unvisited.
bool[,] visited = new bool[n, m];
int result = 0;
// Mark visited all lands
// that are reachable from edge
for(int i = 0; i < n; ++i)
{
for(int j = 0; j < m; ++j)
{
if ((i != 0 && j != 0 &&
i != n - 1 && j != m - 1) &&
matrix[i, j] == 1 &&
visited[i, j] == false)
{
// Determine if the island is closed
bool hasCornerCell = false;
// hasCornerCell will be updated to
// true while DFS traversal if there
// is a cell with value '1' on the corner
dfs(matrix, visited, i, j, n, m,
hasCornerCell);
// If the island is closed
if (!hasCornerCell)
result = result + 1;
}
}
}
// Return the final count
return result;
}
// Driver code
static void Main()
{
// Given size of Matrix
int N = 5, M = 8;
// Given Matrix
int[,] matrix = { { 0, 0, 0, 0, 0, 0, 0, 1 },
{ 0, 1, 1, 1, 1, 0, 0, 1 },
{ 0, 1, 0, 1, 0, 0, 0, 1 },
{ 0, 1, 1, 1, 1, 0, 1, 0 },
{ 0, 0, 0, 0, 0, 0, 0, 1 } };
// Function Call
Console.WriteLine(countClosedIsland(matrix, N, M));
}
}
// This code is contributed by divyesh072019
JavaScript
<script>
// JavaScript program for the above approach
// DFS Traversal to find the count of
// island surrounded by water
function dfs(matrix, visited, x, y, n, m, hasCornerCell)
{
// If the land is already visited
// or there is no land or the
// coordinates gone out of matrix
// break function as there
// will be no islands
if (x < 0 || y < 0 || x >= n || y >= m ||
visited[x][y] == true || matrix[x][y] == 0)
return;
if (x == 0 || y == 0 ||
x == n - 1 || y == m - 1)
{
if (matrix[x][y] == 1)
hasCornerCell = true;
}
// Mark land as visited
visited[x][y] = true;
// Traverse to all adjacent elements
dfs(matrix, visited, x + 1, y, n, m,
hasCornerCell);
dfs(matrix, visited, x, y + 1, n, m,
hasCornerCell);
dfs(matrix, visited, x - 1, y, n, m,
hasCornerCell);
dfs(matrix, visited, x, y - 1, n, m,
hasCornerCell);
}
// Function that counts the closed island
function countClosedIsland(matrix, n, m)
{
// Create boolean 2D visited matrix
// to keep track of visited cell
// Initially all elements are
// unvisited.
let visited = new Array(n);
for(let i = 0; i < n; ++i)
{
visited[i] = new Array(m);
for(let j = 0; j < m; ++j)
{
visited[i][j] = false;
}
}
let result = 0;
// Mark visited all lands
// that are reachable from edge
for(let i = 0; i < n; ++i)
{
for(let j = 0; j < m; ++j)
{
if ((i != 0 && j != 0 &&
i != n - 1 && j != m - 1) &&
matrix[i][j] == 1 &&
visited[i][j] == false)
{
// Determine if the island is closed
let hasCornerCell = false;
// hasCornerCell will be updated to
// true while DFS traversal if there
// is a cell with value '1' on the corner
dfs(matrix, visited, i, j, n, m, hasCornerCell);
// If the island is closed
if (!hasCornerCell)
result = result + 1;
}
}
}
// Return the final count
return result;
}
// Given size of Matrix
let N = 5, M = 8;
// Given Matrix
let matrix = [ [ 0, 0, 0, 0, 0, 0, 0, 1 ],
[ 0, 1, 1, 1, 1, 0, 0, 1 ],
[ 0, 1, 0, 1, 0, 0, 0, 1 ],
[ 0, 1, 1, 1, 1, 0, 1, 0 ],
[ 0, 0, 0, 0, 0, 0, 0, 1 ] ];
// Function Call
document.write(countClosedIsland(matrix, N, M));
</script>
Time Complexity: O(N*M)
The time complexity of the above algorithm is O(N*M) where N and M are the number of rows and columns of the given matrix. We traverse the entire matrix once and then perform a DFS traversal over the islands.
Space Complexity: O(N*M)
The space complexity of the above algorithm is O(N*M) as we declare two boolean arrays of size N*M to keep track of visited cells.
Method 2 - using BFS Traversal: The idea is to visit every cell with value 1 at the corner using BFS and then traverse the given matrix and if any unvisited cell with value 1 is encountered then increment the count of the island and make all the 1s connected to it as visited. Below are the steps:
- Initialize a 2D visited matrix(say vis[][]) to keep the track of traversed cell in the given matrix.
- Perform BFS Traversal on all the corner of the given matrix and if any element has value 1 then marked all the cell with value 1 as visited because it cannot be counted in the resultant count.
- Perform BFS Traversal on all the remaining unvisited cell and if value encountered is 1 then marked this cell as visited, count this island in the resultant count and marked every cell in all the 4 directions i.e., left, right, top, and bottom to make all the 1s connected to the current cell as visited.
- Repeat the above step until all cell with value 1 are not visited.
- Print the count of island after the above steps.
Below is the implementation of the above approach
C++
// C++ program for the above approach
#include <bits/stdc++.h>
using namespace std;
int dx[] = { -1, 0, 1, 0 };
int dy[] = { 0, 1, 0, -1 };
// DFS Traversal to find the count of
// island surrounded by water
void bfs(vector<vector<int> >& matrix,
vector<vector<bool> >& visited,
int x, int y, int n, int m)
{
// To store the popped cell
pair<int, int> temp;
// To store the cell of BFS
queue<pair<int, int> > Q;
// Push the current cell
Q.push({ x, y });
// Until Q is not empty
while (!Q.empty())
{
temp = Q.front();
Q.pop();
// Mark current cell
// as visited
visited[temp.first]
[temp.second]
= true;
// Iterate in all four directions
for (int i = 0; i < 4; i++)
{
int x = temp.first + dx[i];
int y = temp.second + dy[i];
// Cell out of the matrix
if (x < 0 || y < 0
|| x >= n || y >= m
|| visited[x][y] == true
|| matrix[x][y] == 0)
{
continue;
}
// Check is adjacent cell is
// 1 and not visited
if (visited[x][y] == false
&& matrix[x][y] == 1)
{
Q.push({ x, y });
}
}
}
}
// Function that counts the closed island
int countClosedIsland(vector<vector<int> >& matrix,
int n, int m)
{
// Create boolean 2D visited matrix
// to keep track of visited cell
// Initially all elements are
// unvisited.
vector<vector<bool> > visited(
n, vector<bool>(m, false));
// Mark visited all lands
// that are reachable from edge
for (int i = 0; i < n; ++i)
{
for (int j = 0; j < m; ++j)
{
// Traverse corners
if ((i * j == 0
|| i == n - 1
|| j == m - 1)
and matrix[i][j] == 1
and visited[i][j] == false)
{
bfs(matrix, visited,
i, j, n, m);
}
}
}
// To stores number of closed islands
int result = 0;
for (int i = 0; i < n; ++i)
{
for (int j = 0; j < m; ++j)
{
// If the land not visited
// then there will be atleast
// one closed island
if (visited[i][j] == false
and matrix[i][j] == 1)
{
result++;
// Mark all lands associated
// with island visited
bfs(matrix, visited, i, j, n, m);
}
}
}
// Return the final count
return result;
}
// Driver Code
int main()
{
// Given size of Matrix
int N = 5, M = 8;
// Given Matrix
vector<vector<int> > matrix
= { { 0, 0, 0, 0, 0, 0, 0, 1 },
{ 0, 1, 1, 1, 1, 0, 0, 1 },
{ 0, 1, 0, 1, 0, 0, 0, 1 },
{ 0, 1, 1, 1, 1, 0, 1, 0 },
{ 0, 0, 0, 0, 0, 0, 0, 1 } };
// Function Call
cout << countClosedIsland(matrix, N, M);
return 0;
}
Java
// Java program for the above approach
import java.util.LinkedList;
import java.util.Queue;
class GFG{
static int dx[] = { -1, 0, 1, 0 };
static int dy[] = { 0, 1, 0, -1 };
// To store the row and column index
// of the popped cell
static class Cell
{
int first, second;
Cell(int x, int y)
{
this.first = x;
this.second = y;
}
}
// BFS Traversal to find the count of
// island surrounded by water
static void bfs(int[][] matrix, boolean[][] visited,
int x, int y, int n, int m)
{
// To store the popped cell
Cell temp;
// To store the cell of BFS
Queue<Cell> Q = new LinkedList<Cell>();
// Push the current cell
Q.add(new Cell(x, y));
// Until Q is not empty
while (!Q.isEmpty())
{
temp = Q.peek();
Q.poll();
// Mark current cell
// as visited
visited[temp.first][temp.second] = true;
// Iterate in all four directions
for(int i = 0; i < 4; i++)
{
int xIndex = temp.first + dx[i];
int yIndex = temp.second + dy[i];
// Cell out of the matrix
if (xIndex < 0 || yIndex < 0 || xIndex >= n ||
yIndex >= m || visited[xIndex][yIndex] == true ||
matrix[xIndex][yIndex] == 0)
{
continue;
}
// Check is adjacent cell is
// 1 and not visited
if (visited[xIndex][yIndex] == false &&
matrix[xIndex][yIndex] == 1)
{
Q.add(new Cell(xIndex, yIndex));
}
}
}
}
// Function that counts the closed island
static int countClosedIsland(int[][] matrix, int n,
int m)
{
// Create boolean 2D visited matrix
// to keep track of visited cell
// Initially all elements are
// unvisited.
boolean[][] visited = new boolean[n][m];
// Mark visited all lands
// that are reachable from edge
for(int i = 0; i < n; ++i)
{
for(int j = 0; j < m; ++j)
{
// Traverse corners
if ((i * j == 0 || i == n - 1 || j == m - 1) &&
matrix[i][j] == 1 && visited[i][j] == false)
{
bfs(matrix, visited, i, j, n, m);
}
}
}
// To stores number of closed islands
int result = 0;
for(int i = 0; i < n; ++i)
{
for(int j = 0; j < m; ++j)
{
// If the land not visited
// then there will be atleast
// one closed island
if (visited[i][j] == false &&
matrix[i][j] == 1)
{
result++;
// Mark all lands associated
// with island visited
bfs(matrix, visited, i, j, n, m);
}
}
}
// Return the final count
return result;
}
// Driver Code
public static void main(String[] args)
{
// Given size of Matrix
int N = 5, M = 8;
// Given Matrix
int[][] matrix = { { 0, 0, 0, 0, 0, 0, 0, 1 },
{ 0, 1, 1, 1, 1, 0, 0, 1 },
{ 0, 1, 0, 1, 0, 0, 0, 1 },
{ 0, 1, 1, 1, 1, 0, 1, 0 },
{ 0, 0, 0, 0, 0, 0, 0, 1 } };
// Function Call
System.out.println(countClosedIsland(matrix, N, M));
}
}
// This code is contributed by jainlovely450
Python
# Python program for the above approach
dx = [-1, 0, 1, 0 ]
dy = [0, 1, 0, -1]
global matrix
# DFS Traversal to find the count of
# island surrounded by water
def bfs(x, y, n, m):
# To store the popped cell
temp = []
# To store the cell of BFS
Q = []
# Push the current cell
Q.append([x, y])
# Until Q is not empty
while(len(Q) > 0):
temp = Q.pop()
# Mark current cell
# as visited
visited[temp[0]][temp[1]] = True
# Iterate in all four directions
for i in range(4):
x = temp[0] + dx[i]
y = temp[1] + dy[i]
# Cell out of the matrix
if(x < 0 or y < 0 or x >= n or y >= n or visited[x][y] == True or matrix[x][y] == 0):
continue
# Check is adjacent cell is
# 1 and not visited
if(visited[x][y] == False and matrix[x][y] == 1):
Q.append([x, y])
# Function that counts the closed island
def countClosedIsland(n, m):
# Create boolean 2D visited matrix
# to keep track of visited cell
# Initially all elements are
# unvisited.
global visited
visited = [[False for i in range(m)] for j in range(n)]
# Mark visited all lands
# that are reachable from edge
for i in range(n):
for j in range(m):
# Traverse corners
if((i * j == 0 or i == n - 1 or j == m - 1) and matrix[i][j] == 1 and visited[i][j] == False):
bfs(i, j, n, m);
# To stores number of closed islands
result = 0
for i in range(n):
for j in range(m):
# If the land not visited
# then there will be atleast
# one closed island
if(visited[i][j] == False and matrix[i][j] == 1):
result += 1
# Mark all lands associated
# with island visited
bfs(i, j, n, m);
# Return the final count
return result
# Driver Code
# Given size of Matrix
N = 5
M = 8
# Given Matrix
matrix = [[ 0, 0, 0, 0, 0, 0, 0, 1],
[0, 1, 1, 1, 1, 0, 0, 1],
[0, 1, 0, 1, 0, 0, 0, 1 ],
[0, 1, 1, 1, 1, 0, 1, 0 ],
[0, 0, 0, 0, 0, 0, 0, 1]]
# Function Call
print(countClosedIsland(N, M))
# This code is contributed by avanitrachhadiya2155
C#
// C# program for the above approach
using System;
using System.Collections.Generic;
class GFG {
static int[,] matrix;
static bool[,] visited;
static int[] dx = {-1, 0, 1, 0 };
static int[] dy = {0, 1, 0, -1};
// DFS Traversal to find the count of
// island surrounded by water
static void bfs(int x, int y, int n, int m)
{
// To store the popped cell
Tuple<int,int> temp;
// To store the cell of BFS
List<Tuple<int,int>> Q = new List<Tuple<int,int>>();
// Push the current cell
Q.Add(new Tuple<int, int>(x, y));
// Until Q is not empty
while(Q.Count <= 0)
{
temp = Q[0];
Q.RemoveAt(0);
// Mark current cell
// as visited
visited[temp.Item1,temp.Item2] = true;
// Iterate in all four directions
for(int i = 0; i < 4; i++)
{
int xIndex = temp.Item1 + dx[i];
int yIndex = temp.Item2 + dy[i];
// Cell out of the matrix
if (xIndex < 0 || yIndex < 0 || xIndex >= n ||
yIndex >= m || visited[xIndex,yIndex] == true ||
matrix[xIndex,yIndex] == 0)
{
continue;
}
// Check is adjacent cell is
// 1 and not visited
if (visited[xIndex,yIndex] == false &&
matrix[xIndex,yIndex] == 1)
{
Q.Add(new Tuple<int, int>(x, y));
}
}
}
}
// Function that counts the closed island
static int countClosedIsland(int n, int m)
{
// Create boolean 2D visited matrix
// to keep track of visited cell
// Initially all elements are
// unvisited.
visited = new bool[n, m];
for(int i = 0; i < n; i++)
{
for(int j = 0; j < m; j++)
{
visited[i,j] = false;
}
}
// Mark visited all lands
// that are reachable from edge
for(int i = 0; i < n; i++)
{
for(int j = 0; j < m; j++)
{
// Traverse corners
if((i * j == 0 || i == n - 1 || j == m - 1) && matrix[i,j] == 1 && visited[i,j] == false)
{
bfs(i, j, n, m);
}
}
}
// To stores number of closed islands
int result = 2;
for(int i = 0; i < n; i++)
{
for(int j = 0; j < m; j++)
{
// If the land not visited
// then there will be atleast
// one closed island
if(visited[i,j] == false && matrix[i,j] == 1)
{
result = 2;
// Mark all lands associated
// with island visited
bfs(i, j, n, m);
}
}
}
// Return the final count
return result;
}
static void Main() {
// Given size of Matrix
int N = 5, M = 8;
// Given Matrix
matrix = new int[5,8]
{ { 0, 0, 0, 0, 0, 0, 0, 1 },
{ 0, 1, 1, 1, 1, 0, 0, 1 },
{ 0, 1, 0, 1, 0, 0, 0, 1 },
{ 0, 1, 1, 1, 1, 0, 1, 0 },
{ 0, 0, 0, 0, 0, 0, 0, 1 } };
// Function Call
Console.Write(countClosedIsland(N, M));
}
}
// This code is contributed by rameshtravel07.
JavaScript
<script>
// Javascript program for the above approach
let matrix;
let visited;
let dx = [-1, 0, 1, 0 ];
let dy = [0, 1, 0, -1];
// DFS Traversal to find the count of
// island surrounded by water
function bfs(x, y, n, m)
{
// To store the popped cell
let temp;
// To store the cell of BFS
let Q = [];
// Push the current cell
Q.push([x, y]);
// Until Q is not empty
while(Q.length > 0)
{
temp = Q[0];
Q.pop();
// Mark current cell
// as visited
visited[temp[0]][temp[1]] = true;
// Iterate in all four directions
for(let i = 0; i < 4; i++)
{
let x = temp[0] + dx[i];
let y = temp[1] + dy[i];
// Cell out of the matrix
if(x < 0 || y < 0 || x >= n || y >= n || visited[x][y] == true || matrix[x][y] == 0)
{
continue;
}
// Check is adjacent cell is
// 1 and not visited
if(visited[x][y] == false && matrix[x][y] == 1)
{
Q.push([x, y]);
}
}
}
}
// Function that counts the closed island
function countClosedIsland(n, m)
{
// Create boolean 2D visited matrix
// to keep track of visited cell
// Initially all elements are
// unvisited.
visited = new Array(n);
for(let i = 0; i < n; i++)
{
visited[i] = new Array(m);
for(let j = 0; j < m; j++)
{
visited[i][j] = false;
}
}
// Mark visited all lands
// that are reachable from edge
for(let i = 0; i < n; i++)
{
for(let j = 0; j < m; j++)
{
// Traverse corners
if((i * j == 0 || i == n - 1 || j == m - 1) && matrix[i][j] == 1 && visited[i][j] == false)
{
bfs(i, j, n, m);
}
}
}
// To stores number of closed islands
let result = 2;
for(let i = 0; i < n; i++)
{
for(let j = 0; j < m; j++)
{
// If the land not visited
// then there will be atleast
// one closed island
if(visited[i][j] == false && matrix[i][j] == 1)
{
result += 1;
// Mark all lands associated
// with island visited
bfs(i, j, n, m);
}
}
}
// Return the final count
return result;
}
// Given size of Matrix
let N = 5, M = 8;
// Given Matrix
matrix
= [ [ 0, 0, 0, 0, 0, 0, 0, 1 ],
[ 0, 1, 1, 1, 1, 0, 0, 1 ],
[ 0, 1, 0, 1, 0, 0, 0, 1 ],
[ 0, 1, 1, 1, 1, 0, 1, 0 ],
[ 0, 0, 0, 0, 0, 0, 0, 1 ] ];
// Function Call
document.write(countClosedIsland(matrix, N, M));
// This code is contributed by decode2207.
</script>
Time Complexity: O(N*M)
Auxiliary Space: O(N*M)
Method 3 - using Disjoint-Set(Union-Find):
- Traverse the given matrix and change all the 1s and connected at the corners of the matrix to 0s.
- Now traverse the matrix again, and for all set of connected 1s create an edges connecting to all the 1s.
- Find the connected components for all the edges stored using Disjoint-Set Approach.
- Print the count of components after the above steps.
Below is the implementation of the above approach:
C++
// C++ program for the above approach
#include <bits/stdc++.h>
using namespace std;
// Function that implements the Find
int Find(vector<int>& hashSet, int val)
{
// Get the val
int parent = val;
// Until parent is not found
while (parent != hashSet[parent]) {
parent = hashSet[parent];
}
// Return the parent
return parent;
}
// Function that implements the Union
void Union(vector<int>& hashSet,
int first, int second)
{
// Find the first father
int first_father = Find(hashSet, first);
// Find the second father
int second_father = Find(hashSet, second);
// If both are unequals then update
// first father as ssecond_father
if (first_father != second_father)
hashSet[first_father] = second_father;
}
// Recursive Function that change all
// the corners connected 1s to 0s
void change(vector<vector<char> >& matrix,
int x, int y, int n, int m)
{
// If already zero then return
if (x < 0 || y < 0 || x > m - 1
|| y > n - 1 || matrix[x][y] == '0')
return;
// Change the current cell to '0'
matrix[x][y] = '0';
// Recursive Call for all the
// four corners
change(matrix, x + 1, y, n, m);
change(matrix, x, y + 1, n, m);
change(matrix, x - 1, y, n, m);
change(matrix, x, y - 1, n, m);
}
// Function that changes all the
// connected 1s to 0s at the corners
void changeCorner(vector<vector<char> >& matrix)
{
// Dimensions of matrix
int m = matrix.size();
int n = matrix[0].size();
// Traverse the matrix
for (int i = 0; i < m; i++) {
for (int j = 0; j < n; j++) {
// If corner cell
if (i * j == 0 || i == m - 1
|| j == n - 1) {
// If value is 1s, then
// recursively change to 0
if (matrix[i][j] == '1') {
change(matrix, i, j, n, m);
}
}
}
}
}
// Function that counts the number
// of island in the given matrix
int numIslands(vector<vector<char> >& matrix)
{
if (matrix.size() == 0)
return 0;
// Dimensions of the matrix
int m = matrix.size();
int n = matrix[0].size();
// Make all the corners connecting
// 1s to zero
changeCorner(matrix);
// First convert to 1 dimension
// position and convert all the
// connections to edges
vector<pair<int, int> > edges;
for (int i = 0; i < m; i++) {
for (int j = 0; j < n; j++) {
// If the cell value is 1
if (matrix[i][j] == '1') {
int id = i * n + j;
// Move right
if (j + 1 < n) {
// If right cell is
// 1 then make it as
// an edge
if (matrix[i][j + 1] == '1') {
int right = i * n + j + 1;
// Push in edge vector
edges.push_back(make_pair(id, right));
}
}
// Move down
if (i + 1 < m) {
// If right cell is
// 1 then make it as
// an edge
if (matrix[i + 1][j] == '1') {
int down = (i + 1) * n + j;
// Push in edge vector
edges.push_back(make_pair(id, down));
}
}
}
}
}
// Construct the Union Find structure
vector<int> hashSet(m * n, 0);
for (int i = 0; i < m * n; i++) {
hashSet[i] = i;
}
// Next apply Union Find for all
// the edges stored
for (auto edge : edges) {
Union(hashSet, edge.first, edge.second);
}
// To count the number of connected
// islands
int numComponents = 0;
// Traverse to find the islands
for (int i = 0; i < m * n; i++) {
if (matrix[i / n][i % n] == '1'
&& hashSet[i] == i)
numComponents++;
}
// Return the count of the island
return numComponents;
}
// Driver Code
int main()
{
// Given size of Matrix
int N = 5, M = 8;
// Given Matrix
vector<vector<char> > matrix
= { { '0', '0', '0', '0', '0', '0', '0', '1' },
{ '0', '1', '1', '1', '1', '0', '0', '1' },
{ '0', '1', '0', '1', '0', '0', '0', '1' },
{ '0', '1', '1', '1', '1', '0', '1', '0' },
{ '0', '0', '0', '0', '0', '0', '0', '1' } };
// Function Call
cout << numIslands(matrix);
return 0;
}
Java
// Java program for the above approach
import java.util.ArrayList;
class GFG{
static class Edge
{
int first, second;
Edge(int x, int y)
{
this.first = x;
this.second = y;
}
}
// Function that implements the Find
static int Find(int[] hashSet, int val)
{
// Get the val
int parent = val;
// Until parent is not found
while (parent != hashSet[parent])
{
parent = hashSet[parent];
}
// Return the parent
return parent;
}
// Function that implements the Union
static void Union(int[] hashSet, int first, int second)
{
// Find the first father
int first_father = Find(hashSet, first);
// Find the second father
int second_father = Find(hashSet, second);
// If both are unequals then update
// first father as ssecond_father
if (first_father != second_father)
hashSet[first_father] = second_father;
}
// Recursive Function that change all
// the corners connected 1s to 0s
static void change(char[][] matrix, int x, int y,
int n, int m)
{
// If already zero then return
if (x < 0 || y < 0 || x > m - 1 ||
y > n - 1 || matrix[x][y] == '0')
return;
// Change the current cell to '0'
matrix[x][y] = '0';
// Recursive Call for all the
// four corners
change(matrix, x + 1, y, n, m);
change(matrix, x, y + 1, n, m);
change(matrix, x - 1, y, n, m);
change(matrix, x, y - 1, n, m);
}
// Function that changes all the
// connected 1s to 0s at the corners
static void changeCorner(char[][] matrix)
{
// Dimensions of matrix
int m = matrix.length;
int n = matrix[0].length;
// Traverse the matrix
for(int i = 0; i < m; i++)
{
for(int j = 0; j < n; j++)
{
// If corner cell
if (i * j == 0 || i == m - 1 || j == n - 1)
{
// If value is 1s, then
// recursively change to 0
if (matrix[i][j] == '1')
{
change(matrix, i, j, n, m);
}
}
}
}
}
// Function that counts the number
// of island in the given matrix
static int numIslands(char[][] matrix)
{
if (matrix.length == 0)
return 0;
// Dimensions of the matrix
int m = matrix.length;
int n = matrix[0].length;
// Make all the corners connecting
// 1s to zero
changeCorner(matrix);
// First convert to 1 dimension
// position and convert all the
// connections to edges
ArrayList<Edge> edges = new ArrayList<Edge>();
for(int i = 0; i < m; i++)
{
for(int j = 0; j < n; j++)
{
// If the cell value is 1
if (matrix[i][j] == '1')
{
int id = i * n + j;
// Move right
if (j + 1 < n)
{
// If right cell is
// 1 then make it as
// an edge
if (matrix[i][j + 1] == '1')
{
int right = i * n + j + 1;
// Push in edge vector
edges.add(new Edge(id, right));
}
}
// Move down
if (i + 1 < m)
{
// If right cell is
// 1 then make it as
// an edge
if (matrix[i + 1][j] == '1')
{
int down = (i + 1) * n + j;
// Push in edge vector
edges.add(new Edge(id, down));
}
}
}
}
}
// Construct the Union Find structure
int[] hashSet = new int[m * n];
for(int i = 0; i < m * n; i++)
{
hashSet[i] = i;
}
// Next apply Union Find for all
// the edges stored
for(Edge edge : edges)
{
Union(hashSet, edge.first, edge.second);
}
// To count the number of connected
// islands
int numComponents = 0;
// Traverse to find the islands
for(int i = 0; i < m * n; i++)
{
if (matrix[i / n][i % n] == '1' &&
hashSet[i] == i)
numComponents++;
}
// Return the count of the island
return numComponents;
}
// Driver Code
public static void main(String[] args)
{
// Given size of Matrix
int N = 5, M = 8;
// Given Matrix
char[][] matrix = { { '0', '0', '0', '0',
'0', '0', '0', '1' },
{ '0', '1', '1', '1',
'1', '0', '0', '1' },
{ '0', '1', '0', '1',
'0', '0', '0', '1' },
{ '0', '1', '1', '1',
'1', '0', '1', '0' },
{ '0', '0', '0', '0',
'0', '0', '0', '1' } };
// Function Call
System.out.println(numIslands(matrix));
}
}
// This code is contributed by jainlovely450
Python
# python 3 program for the above approach
# Function that implements the Find
def Find(hashSet, val):
# Get the val
parent = val
# Until parent is not found
while (parent != hashSet[parent]):
parent = hashSet[parent]
# Return the parent
return parent
# Function that implements the Union
def Union(hashSet, first, second):
# Find the first father
first_father = Find(hashSet, first)
# Find the second father
second_father = Find(hashSet, second)
# If both are unequals then update
# first father as ssecond_father
if (first_father != second_father):
hashSet[first_father] = second_father
# Recursive Function that change all
# the corners connected 1s to 0s
def change(matrix, x, y, n, m):
# If already zero then return
if (x < 0 or y < 0 or x > m - 1 or y > n - 1 or matrix[x][y] == '0'):
return
# Change the current cell to '0'
matrix[x][y] = '0'
# Recursive Call for all the
# four corners
change(matrix, x + 1, y, n, m)
change(matrix, x, y + 1, n, m)
change(matrix, x - 1, y, n, m)
change(matrix, x, y - 1, n, m)
# Function that changes all the
# connected 1s to 0s at the corners
def changeCorner(matrix):
# Dimensions of matrix
m = len(matrix)
n = len(matrix[0])
# Traverse the matrix
for i in range(m):
for j in range(n):
# If corner cell
if (i * j == 0 or i == m - 1 or j == n - 1):
# If value is 1s, then
# recursively change to 0
if (matrix[i][j] == '1'):
change(matrix, i, j, n, m)
# Function that counts the number
# of island in the given matrix
def numIslands(matrix):
if (len(matrix) == 0):
return 0
# Dimensions of the matrix
m = len(matrix)
n = len(matrix[0])
# Make all the corners connecting
# 1s to zero
changeCorner(matrix)
# First convert to 1 dimension
# position and convert all the
# connections to edges
edges = []
for i in range(m):
for j in range(n):
# If the cell value is 1
if (matrix[i][j] == '1'):
id = i * n + j
# Move right
if (j + 1 < n):
# If right cell is
# 1 then make it as
# an edge
if (matrix[i][j + 1] == '1'):
right = i * n + j + 1
# Push in edge vector
edges.append([id, right])
# Move down
if (i + 1 < m):
# If right cell is
# 1 then make it as
# an edge
if (matrix[i + 1][j] == '1'):
down = (i + 1) * n + j
# Push in edge vector
edges.append([id, down])
# Construct the Union Find structure
hashSet = [0 for i in range(m*n)]
for i in range(m*n):
hashSet[i] = i
# Next apply Union Find for all
# the edges stored
for edge in edges:
Union(hashSet, edge[0], edge[1])
# To count the number of connected
# islands
numComponents = 0
# Traverse to find the islands
for i in range(m*n):
if (matrix[i // n][i % n] == '1' and hashSet[i] == i):
numComponents += 1
# Return the count of the island
return numComponents
# Driver Code
if __name__ == '__main__':
# Given size of Matrix
N = 5
M = 8
# Given Matrix
matrix = [['0', '0', '0', '0', '0', '0', '0', '1'],
['0', '1', '1', '1', '1', '0', '0', '1'],
['0', '1', '0', '1', '0', '0', '0', '1'],
['0', '1', '1', '1', '1', '0', '1', '0'],
['0', '0', '0', '0', '0', '0', '0', '1']]
# Function Call
print(numIslands(matrix))
# This code is contributed by bgangwar59.
C#
using System;
using System.Collections.Generic;
class Program
{
static int Find(List<int> hashSet, int val)
{
int parent = val;
while (parent != hashSet[parent])
{
parent = hashSet[parent];
}
return parent;
}
static void Union(List<int> hashSet, int first, int second)
{
int first_father = Find(hashSet, first);
int second_father = Find(hashSet, second);
if (first_father != second_father)
hashSet[first_father] = second_father;
}
static void Change(ref List<List<char>> matrix, int x, int y, int n, int m)
{
if (x < 0 || y < 0 || x > m - 1 || y > n - 1 || matrix[x][y] == '0')
return;
matrix[x][y] = '0';
Change(ref matrix, x + 1, y, n, m);
Change(ref matrix, x, y + 1, n, m);
Change(ref matrix, x - 1, y, n, m);
Change(ref matrix, x, y - 1, n, m);
}
static void ChangeCorner(ref List<List<char>> matrix)
{
int m = matrix.Count;
int n = matrix[0].Count;
for (int i = 0; i < m; i++)
{
for (int j = 0; j < n; j++)
{
if (i * j == 0 || i == m - 1 || j == n - 1)
{
if (matrix[i][j] == '1')
{
Change(ref matrix, i, j, n, m);
}
}
}
}
}
static int NumIslands(List<List<char>> matrix)
{
if (matrix.Count == 0)
return 0;
int m = matrix.Count;
int n = matrix[0].Count;
ChangeCorner(ref matrix);
List<Tuple<int, int>> edges = new List<Tuple<int, int>>();
for (int i = 0; i < m; i++)
{
for (int j = 0; j < n; j++)
{
if (matrix[i][j] == '1')
{
int id = i * n + j;
if (j + 1 < n)
{
if (matrix[i][j + 1] == '1')
{
int right = i * n + j + 1;
edges.Add(new Tuple<int, int>(id, right));
}
}
if (i + 1 < m)
{
if (matrix[i + 1][j] == '1')
{
int down = (i + 1) * n + j;
edges.Add(new Tuple<int, int>(id, down));
}
}
}
}
}
List<int> hashSet = new List<int>(m * n);
for (int i = 0; i < m * n; i++)
{
hashSet.Add(i);
}
foreach (Tuple<int, int> edge in edges)
{
Union(hashSet, edge.Item1, edge.Item2);
}
int numComponents = 0;
for (int i = 0; i < m * n; i++)
if (matrix[i / n][i %n] == '1' && hashSet[i]==i)
numComponents++;
return numComponents;
}
public static void Main()
{
// Given size of Matrix
int N = 5, M = 8;
// Given Matrix
List<List<char>> matrix = new List<List<char>>() {
new List<char> { '0', '0', '0', '0', '0', '0', '0', '1' },
new List<char> { '0', '1', '1', '1', '1', '0', '0', '1' },
new List<char> { '0', '1', '0', '1', '0', '0', '0', '1' },
new List<char> { '0', '1', '1', '1', '1', '0', '1', '0' },
new List<char> { '0', '0', '0', '0', '0', '0', '0', '1' }
};
// Function Call
Console.WriteLine(NumIslands(matrix));
}
}
JavaScript
<script>
// JavaScript program for the above approach
// Function that implements the Find
function Find(hashSet, val)
{
// Get the val
var parent = val;
// Until parent is not found
while (parent != hashSet[parent]) {
parent = hashSet[parent];
}
// Return the parent
return parent;
}
// Function that implements the Union
function Union(hashSet, first, second) {
// Find the first father
var first_father = Find(hashSet, first);
// Find the second father
var second_father = Find(hashSet, second);
// If both are unequals then update
// first father as ssecond_father
if (first_father != second_father) {
hashSet[first_father] = second_father;
}
}
// Recursive Function that change all
// the corners connected 1s to 0s
function change(matrix, x, y, n, m) {
// If already zero then return
if (x < 0 || y < 0 || x > m - 1 || y > n - 1 || matrix[x][y] == "0") {
return;
}
// Change the current cell to '0'
matrix[x][y] = "0";
// Recursive Call for all the
// four corners
change(matrix, x + 1, y, n, m);
change(matrix, x, y + 1, n, m);
change(matrix, x - 1, y, n, m);
change(matrix, x, y - 1, n, m);
}
// Function that changes all the
// connected 1s to 0s at the corners
function changeCorner(matrix) {
// Dimensions of matrix
var m = matrix.length;
var n = matrix[0].length;
// Traverse the matrix
for (let i = 0; i < m; i++) {
for (let j = 0; j < n; j++) {
// If corner cell
if (i * j == 0 || i == m - 1 || j == n - 1) {
// If value is 1s, then
// recursively change to 0
if (matrix[i][j] == "1") {
change(matrix, i, j, n, m);
}
}
}
}
}
// Function that counts the number
// of island in the given matrix
function numIslands(matrix) {
if (matrix.length == 0) {
return 0;
}
// Dimensions of the matrix
var m = matrix.length;
var n = matrix[0].length;
// Make all the corners connecting
// 1s to zero
changeCorner(matrix);
// First convert to 1 dimension
// position and convert all the
// connections to edges
var edges = [];
for (let i = 0; i < m; i++) {
for (let j = 0; j < n; j++) {
// If the cell value is 1
if (matrix[i][j] == "1") {
id = i * n + j;
// Move right
if (j + 1 < n) {
// If right cell is
// 1 then make it as
// an edge
if (matrix[i][j + 1] == "1") {
var right = i * n + j + 1;
// Push in edge vector
edges.push([id, right]);
}
}
// Move down
if (i + 1 < m) {
// If right cell is
// 1 then make it as
// an edge
if (matrix[i + 1][j] == "1") {
var down = (i + 1) * n + j;
// Push in edge vector
edges.push([id, down]);
}
}
}
}
}
// Construct the Union Find structure
var hashSet = Array(m * n).fill(0);
for (let i = 0; i < m * n; i++) {
hashSet[i] = i;
}
// Next apply Union Find for all
// the edges stored
for (let i =0; i<edges.length; i++ ) {
Union(hashSet, edges[i][0], edges[i][1]);
}
// To count the number of connected
// islands
var numComponents = 0;
// Traverse to find the islands
for (let i = 0; i < m * n; i++) {
if (matrix[parseInt(i / n)][i % n] == "1" && hashSet[i] == i) {
numComponents += 1;
}
}
// Return the count of the island
return numComponents;
}
// Driver Code
// Given size of Matrix
var N = 5;
var M = 8;
// Given Matrix
var matrix = [
["0", "0", "0", "0", "0", "0", "0", "1"],
["0", "1", "1", "1", "1", "0", "0", "1"],
["0", "1", "0", "1", "0", "0", "0", "1"],
["0", "1", "1", "1", "1", "0", "1", "0"],
["0", "0", "0", "0", "0", "0", "0", "1"],
];
// Function Call
document.write(numIslands(matrix));
// This code is contributed by rdtank.
</script>
Time Complexity: O(N*M)
Auxiliary Space: O(N*M)
Similar Reads
Basics & Prerequisites
Data Structures
Getting Started with Array Data StructureArray is a collection of items of the same variable type that are stored at contiguous memory locations. It is one of the most popular and simple data structures used in programming. Basic terminologies of ArrayArray Index: In an array, elements are identified by their indexes. Array index starts fr
14 min read
String in Data StructureA string is a sequence of characters. The following facts make string an interesting data structure.Small set of elements. Unlike normal array, strings typically have smaller set of items. For example, lowercase English alphabet has only 26 characters. ASCII has only 256 characters.Strings are immut
2 min read
Hashing in Data StructureHashing is a technique used in data structures that efficiently stores and retrieves data in a way that allows for quick access. Hashing involves mapping data to a specific index in a hash table (an array of items) using a hash function. It enables fast retrieval of information based on its key. The
2 min read
Linked List Data StructureA linked list is a fundamental data structure in computer science. It mainly allows efficient insertion and deletion operations compared to arrays. Like arrays, it is also used to implement other data structures like stack, queue and deque. Hereâs the comparison of Linked List vs Arrays Linked List:
2 min read
Stack Data StructureA Stack is a linear data structure that follows a particular order in which the operations are performed. The order may be LIFO(Last In First Out) or FILO(First In Last Out). LIFO implies that the element that is inserted last, comes out first and FILO implies that the element that is inserted first
2 min read
Queue Data StructureA Queue Data Structure is a fundamental concept in computer science used for storing and managing data in a specific order. It follows the principle of "First in, First out" (FIFO), where the first element added to the queue is the first one to be removed. It is used as a buffer in computer systems
2 min read
Tree Data StructureTree Data Structure is a non-linear data structure in which a collection of elements known as nodes are connected to each other via edges such that there exists exactly one path between any two nodes. Types of TreeBinary Tree : Every node has at most two childrenTernary Tree : Every node has at most
4 min read
Graph Data StructureGraph Data Structure is a collection of nodes connected by edges. It's used to represent relationships between different entities. If you are looking for topic-wise list of problems on different topics like DFS, BFS, Topological Sort, Shortest Path, etc., please refer to Graph Algorithms. Basics of
3 min read
Trie Data StructureThe Trie data structure is a tree-like structure used for storing a dynamic set of strings. It allows for efficient retrieval and storage of keys, making it highly effective in handling large datasets. Trie supports operations such as insertion, search, deletion of keys, and prefix searches. In this
15+ min read
Algorithms
Searching AlgorithmsSearching algorithms are essential tools in computer science used to locate specific items within a collection of data. In this tutorial, we are mainly going to focus upon searching in an array. When we search an item in an array, there are two most common algorithms used based on the type of input
2 min read
Sorting AlgorithmsA Sorting Algorithm is used to rearrange a given array or list of elements in an order. For example, a given array [10, 20, 5, 2] becomes [2, 5, 10, 20] after sorting in increasing order and becomes [20, 10, 5, 2] after sorting in decreasing order. There exist different sorting algorithms for differ
3 min read
Introduction to RecursionThe process in which a function calls itself directly or indirectly is called recursion and the corresponding function is called a recursive function. A recursive algorithm takes one step toward solution and then recursively call itself to further move. The algorithm stops once we reach the solution
14 min read
Greedy AlgorithmsGreedy algorithms are a class of algorithms that make locally optimal choices at each step with the hope of finding a global optimum solution. At every step of the algorithm, we make a choice that looks the best at the moment. To make the choice, we sometimes sort the array so that we can always get
3 min read
Graph AlgorithmsGraph is a non-linear data structure like tree data structure. The limitation of tree is, it can only represent hierarchical data. For situations where nodes or vertices are randomly connected with each other other, we use Graph. Example situations where we use graph data structure are, a social net
3 min read
Dynamic Programming or DPDynamic Programming is an algorithmic technique with the following properties.It is mainly an optimization over plain recursion. Wherever we see a recursive solution that has repeated calls for the same inputs, we can optimize it using Dynamic Programming. The idea is to simply store the results of
3 min read
Bitwise AlgorithmsBitwise algorithms in Data Structures and Algorithms (DSA) involve manipulating individual bits of binary representations of numbers to perform operations efficiently. These algorithms utilize bitwise operators like AND, OR, XOR, NOT, Left Shift, and Right Shift.BasicsIntroduction to Bitwise Algorit
4 min read
Advanced
Segment TreeSegment Tree is a data structure that allows efficient querying and updating of intervals or segments of an array. It is particularly useful for problems involving range queries, such as finding the sum, minimum, maximum, or any other operation over a specific range of elements in an array. The tree
3 min read
Pattern SearchingPattern searching algorithms are essential tools in computer science and data processing. These algorithms are designed to efficiently find a particular pattern within a larger set of data. Patten SearchingImportant Pattern Searching Algorithms:Naive String Matching : A Simple Algorithm that works i
2 min read
GeometryGeometry is a branch of mathematics that studies the properties, measurements, and relationships of points, lines, angles, surfaces, and solids. From basic lines and angles to complex structures, it helps us understand the world around us.Geometry for Students and BeginnersThis section covers key br
2 min read
Interview Preparation
Practice Problem