Given n nodes of a forest (collection of trees), find the number of trees in the forest.
Examples :
Input : edges[] = {0, 1}, {0, 2}, {3, 4}
Output : 2
Explanation : There are 2 trees
0 3
/ \ \
1 2 4
Approach :
- Apply DFS on every node.
- Increment count by one if every connected node is visited from one source.
- Again perform DFS traversal if some nodes yet not visited.
- Count will give the number of trees in forest.
Implementation:
// CPP program to count number of trees in
// a forest.
#include<bits/stdc++.h>
using namespace std;
// A utility function to add an edge in an
// undirected graph.
void addEdge(vector<int> adj[], int u, int v)
{
adj[u].push_back(v);
adj[v].push_back(u);
}
// A utility function to do DFS of graph
// recursively from a given vertex u.
void DFSUtil(int u, vector<int> adj[],
vector<bool> &visited)
{
visited[u] = true;
for (int i=0; i<adj[u].size(); i++)
if (visited[adj[u][i]] == false)
DFSUtil(adj[u][i], adj, visited);
}
// Returns count of tree is the forest
// given as adjacency list.
int countTrees(vector<int> adj[], int V)
{
vector<bool> visited(V, false);
int res = 0;
for (int u=0; u<V; u++)
{
if (visited[u] == false)
{
DFSUtil(u, adj, visited);
res++;
}
}
return res;
}
// Driver code
int main()
{
int V = 5;
vector<int> adj[V];
addEdge(adj, 0, 1);
addEdge(adj, 0, 2);
addEdge(adj, 3, 4);
cout << countTrees(adj, V);
return 0;
}
// Java program to count number of trees in a forest.
import java.io.*;
import java.util.*;
// This class represents a directed graph using adjacency list
// representation
class Graph
{
private int V; // No. of vertices
// Array of lists for Adjacency List Representation
private LinkedList<Integer> adj[];
// Constructor
Graph(int v)
{
V = v;
adj = new LinkedList[v];
for (int i = 0; i < v; ++i)
adj[i] = new LinkedList();
}
//Function to add an edge into the graph
void addEdge(int v, int w)
{
adj[v].add(w); // Add w to v's list.
}
// A function used by DFS
void DFSUtil(int v,boolean visited[])
{
// Mark the current node as visited and print it
visited[v] = true;
// Recur for all the vertices adjacent to this vertex
Iterator<Integer> i = adj[v].listIterator();
while (i.hasNext())
{
int n = i.next();
if (!visited[n])
{
DFSUtil(n,visited);
}
}
}
// The function to do DFS traversal. It uses recursive DFSUtil()
int countTrees()
{
// Mark all the vertices as not visited(set as
// false by default in java)
boolean visited[] = new boolean[V];
int res = 0;
// Call the recursive helper function to print DFS traversal
// starting from all vertices one by one
for (int i = 0; i < V; ++i)
{
if (visited[i] == false)
{
DFSUtil(i, visited);
res ++;
}
}
return res;
}
// Driver code
public static void main(String args[])
{
Graph g = new Graph(5);
g.addEdge(0, 1);
g.addEdge(0, 2);
g.addEdge(3, 4);
System.out.println(g.countTrees());
}
}
// This code is contributed by mayankbansal2
# Python3 program to count number
# of trees in a forest.
# A utility function to add an
# edge in an undirected graph.
def addEdge(adj, u, v):
adj[u].append(v)
adj[v].append(u)
# A utility function to do DFS of graph
# recursively from a given vertex u.
def DFSUtil(u, adj, visited):
visited[u] = True
for i in range(len(adj[u])):
if (visited[adj[u][i]] == False):
DFSUtil(adj[u][i], adj, visited)
# Returns count of tree is the
# forest given as adjacency list.
def countTrees(adj, V):
visited = [False] * V
res = 0
for u in range(V):
if (visited[u] == False):
DFSUtil(u, adj, visited)
res += 1
return res
# Driver code
if __name__ == '__main__':
V = 5
adj = [[] for i in range(V)]
addEdge(adj, 0, 1)
addEdge(adj, 0, 2)
addEdge(adj, 3, 4)
print(countTrees(adj, V))
# This code is contributed by PranchalK
// C# program to count number of trees in a forest.
using System;
using System.Collections.Generic;
// This class represents a directed graph
// using adjacency list representation
class Graph
{
private int V; // No. of vertices
// Array of lists for
// Adjacency List Representation
private List<int> []adj;
// Constructor
Graph(int v)
{
V = v;
adj = new List<int>[v];
for (int i = 0; i < v; ++i)
adj[i] = new List<int>();
}
// Function to add an edge into the graph
void addEdge(int v, int w)
{
adj[v].Add(w); // Add w to v's list.
}
// A function used by DFS
void DFSUtil(int v, bool []visited)
{
// Mark the current node as
// visited and print it
visited[v] = true;
// Recur for all the vertices
// adjacent to this vertex
foreach(int i in adj[v])
{
int n = i;
if (!visited[n])
{
DFSUtil(n, visited);
}
}
}
// The function to do DFS traversal.
// It uses recursive DFSUtil()
int countTrees()
{
// Mark all the vertices as not visited
// (set as false by default in java)
bool []visited = new bool[V];
int res = 0;
// Call the recursive helper function
// to print DFS traversal starting from
// all vertices one by one
for (int i = 0; i < V; ++i)
{
if (visited[i] == false)
{
DFSUtil(i, visited);
res ++;
}
}
return res;
}
// Driver code
public static void Main(String []args)
{
Graph g = new Graph(5);
g.addEdge(0, 1);
g.addEdge(0, 2);
g.addEdge(3, 4);
Console.WriteLine(g.countTrees());
}
}
// This code is contributed by PrinciRaj1992
<script>
// Javascript program to count number of trees in a forest.
// This class represents a directed graph
// using adjacency list representation
var V; // No. of vertices
// Array of lists for
// Adjacency List Representation
var adj;
// Constructor
function Graph( v)
{
V = v;
adj = Array.from(Array(v), ()=>Array());
}
// Function to add an edge into the graph
function addEdge(v, w)
{
adj[v].push(w); // Add w to v's list.
}
// A function used by DFS
function DFSUtil(v, visited)
{
// Mark the current node as
// visited and print it
visited[v] = true;
// Recur for all the vertices
// adjacent to this vertex
for(var i of adj[v])
{
var n = i;
if (!visited[n])
{
DFSUtil(n, visited);
}
}
}
// The function to do DFS traversal.
// It uses recursive DFSUtil()
function countTrees()
{
// Mark all the vertices as not visited
// (set as false by default in java)
var visited = Array(V).fill(false);
var res = 0;
// Call the recursive helper function
// to print DFS traversal starting from
// all vertices one by one
for(var i = 0; i < V; ++i)
{
if (visited[i] == false)
{
DFSUtil(i, visited);
res ++;
}
}
return res;
}
// Driver code
Graph(5);
addEdge(0, 1);
addEdge(0, 2);
addEdge(3, 4);
document.write(countTrees());
// This code is contributed by rutvik_56.
</script>
Output
2
Time Complexity: O(V + E), where V is the number of vertices and E is the number of edges.
Space Complexity: O(V). We use an array of size V to store the visited nodes.
Approach:- Here's an implementation of counting the number of trees in a forest using BFS in C++
- Define a bfs function that takes the forest, a start node, and a visited array as inputs. The function performs BFS starting from the start node and marks all visited nodes in the visited array.
- Inside the bfs function, create a queue q to store the nodes that are to be visited in the BFS. Initially, push the start node onto the queue and mark it as visited in the visited array.
#include <iostream>
#include <queue>
#include <vector>
using namespace std;
// define a pair to represent a node in the forest
typedef pair<int, int> Node;
// function to perform BFS from a given node and mark all visited nodes
void bfs(vector<vector<int>>& forest, Node start, vector<vector<bool>>& visited) {
// create a queue for BFS
queue<Node> q;
q.push(start);
visited[start.first][start.second] = true;
// BFS loop
while (!q.empty()) {
Node curr = q.front();
q.pop();
// add unvisited neighboring nodes to the queue
int dx[] = {-1, 0, 1, 0};
int dy[] = {0, 1, 0, -1};
for (int i = 0; i < 4; i++) {
int nx = curr.first + dx[i];
int ny = curr.second + dy[i];
if (nx >= 0 && nx < forest.size() && ny >= 0 && ny < forest[0].size() && forest[nx][ny] == 1 && !visited[nx][ny]) {
q.push(make_pair(nx, ny));
visited[nx][ny] = true;
}
}
}
}
// function to count the number of trees in a forest using BFS
int count_trees_in_forest(vector<vector<int>>& forest) {
int count = 0;
int n = forest.size();
int m = forest[0].size();
// create a 2D boolean array to keep track of visited nodes
vector<vector<bool>> visited(n, vector<bool>(m, false));
// iterate over all nodes in the forest and perform BFS from each unvisited tree
for (int i = 0; i < n; i++) {
for (int j = 0; j < m; j++) {
if (forest[i][j] == 1 && !visited[i][j]) {
bfs(forest, make_pair(i, j), visited);
count++;
}
}
}
return count;
}
int main() {
// example usage
vector<vector<int>> forest = {
{0, 1, 1, 0, 0},
{0, 0, 0, 0, 0},
{0, 0, 0, 0, 0},
{0, 0, 0, 0, 1},
{0, 0, 0, 0, 0}
};
int num_trees = count_trees_in_forest(forest);
cout << "The forest has " << num_trees << " trees." << endl;
return 0;
}
import java.util.*;
public class Forest {
// define a pair to represent a node in the forest
static class Node {
int x;
int y;
Node(int x, int y) {
this.x = x;
this.y = y;
}
}
// function to perform BFS from a given node and mark all visited nodes
static void bfs(int[][] forest, Node start, boolean[][] visited) {
// create a queue for BFS
Queue<Node> q = new LinkedList<>();
q.add(start);
visited[start.x][start.y] = true;
// BFS loop
while (!q.isEmpty()) {
Node curr = q.poll();
// add unvisited neighboring nodes to the queue
int[] dx = {-1, 0, 1, 0};
int[] dy = {0, 1, 0, -1};
for (int i = 0; i < 4; i++) {
int nx = curr.x + dx[i];
int ny = curr.y + dy[i];
if (nx >= 0 && nx < forest.length && ny >= 0 && ny < forest[0].length && forest[nx][ny] == 1 && !visited[nx][ny]) {
q.add(new Node(nx, ny));
visited[nx][ny] = true;
}
}
}
}
// function to count the number of trees in a forest using BFS
static int count_trees_in_forest(int[][] forest) {
int count = 0;
int n = forest.length;
int m = forest[0].length;
// create a 2D boolean array to keep track of visited nodes
boolean[][] visited = new boolean[n][m];
// iterate over all nodes in the forest and perform BFS from each unvisited tree
for (int i = 0; i < n; i++) {
for (int j = 0; j < m; j++) {
if (forest[i][j] == 1 && !visited[i][j]) {
bfs(forest, new Node(i, j), visited);
count++;
}
}
}
return count;
}
public static void main(String[] args) {
// example usage
int[][] forest = {
{0, 1, 1, 0, 0},
{0, 0, 0, 0, 0},
{0, 0, 0, 0, 0},
{0, 0, 0, 0, 1},
{0, 0, 0, 0, 0}
};
int num_trees = count_trees_in_forest(forest);
System.out.println("The forest has " + num_trees + " trees.");
}
}
from typing import List, Tuple
from queue import Queue
# define a tuple to represent a node in the forest
Node = Tuple[int, int]
# function to perform BFS from a given node and mark all visited nodes
def bfs(forest: List[List[int]], start: Node, visited: List[List[bool]]) -> None:
# create a queue for BFS
q = Queue()
q.put(start)
visited[start[0]][start[1]] = True
# BFS loop
while not q.empty():
curr = q.get()
# add unvisited neighboring nodes to the queue
dx = [-1, 0, 1, 0]
dy = [0, 1, 0, -1]
for i in range(4):
nx = curr[0] + dx[i]
ny = curr[1] + dy[i]
if 0 <= nx < len(forest) and 0 <= ny < len(forest[0]) and forest[nx][ny] == 1 and not visited[nx][ny]:
q.put((nx, ny))
visited[nx][ny] = True
# function to count the number of trees in a forest using BFS
def count_trees_in_forest(forest: List[List[int]]) -> int:
count = 0
n, m = len(forest), len(forest[0])
# create a 2D boolean array to keep track of visited nodes
visited = [[False for _ in range(m)] for _ in range(n)]
# iterate over all nodes in the forest and perform BFS from each unvisited tree
for i in range(n):
for j in range(m):
if forest[i][j] == 1 and not visited[i][j]:
bfs(forest, (i, j), visited)
count += 1
return count
# example usage
forest = [
[0, 1, 1, 0, 0],
[0, 0, 0, 0, 0],
[0, 0, 0, 0, 0],
[0, 0, 0, 0, 1],
[0, 0, 0, 0, 0]
]
num_trees = count_trees_in_forest(forest)
print(f"The forest has {num_trees} trees.")
// C# code for above mentioned approach
using System;
using System.Collections.Generic;
class Program {
// define a pair to represent a node in the forest
class Node {
public int x;
public int y;
public Node(int x, int y)
{
this.x = x;
this.y = y;
}
}
// function to perform BFS from a given node and mark
// all visited nodes
static void bfs(int[][] forest, Node start,
bool[][] visited)
{
// create a queue for BFS
Queue<Node> q = new Queue<Node>();
q.Enqueue(start);
visited[start.x][start.y] = true;
// BFS loop
while (q.Count != 0) {
Node curr = q.Dequeue();
// add unvisited neighboring nodes to the queue
int[] dx = { -1, 0, 1, 0 };
int[] dy = { 0, 1, 0, -1 };
for (int i = 0; i < 4; i++) {
int nx = curr.x + dx[i];
int ny = curr.y + dy[i];
if (nx >= 0 && nx < forest.Length && ny >= 0
&& ny < forest[0].Length
&& forest[nx][ny] == 1
&& !visited[nx][ny]) {
q.Enqueue(new Node(nx, ny));
visited[nx][ny] = true;
}
}
}
}
// function to count the number of trees in a forest
// using BFS
static int count_trees_in_forest(int[][] forest)
{
int count = 0;
int n = forest.Length;
int m = forest[0].Length;
// create a 2D boolean array to keep track of
// visited nodes
bool[][] visited = new bool[n][];
for (int i = 0; i < n; i++) {
visited[i] = new bool[m];
}
// iterate over all nodes in the forest and perform
// BFS from each unvisited tree
for (int i = 0; i < n; i++) {
for (int j = 0; j < m; j++) {
if (forest[i][j] == 1 && !visited[i][j]) {
bfs(forest, new Node(i, j), visited);
count++;
}
}
}
return count;
}
static void Main(string[] args)
{
// example usage
int[][] forest = { new int[] { 0, 1, 1, 0, 0 },
new int[] { 0, 0, 0, 0, 0 },
new int[] { 0, 0, 0, 0, 0 },
new int[] { 0, 0, 0, 0, 1 },
new int[] { 0, 0, 0, 0, 0 } };
int num_trees = count_trees_in_forest(forest);
Console.WriteLine("The forest has " + num_trees
+ " trees.");
}
}
// This code is contributed by Tapesh(tapeshdua420)
// define a pair to represent a node in the forest
class Node {
constructor(x, y) {
this.x = x;
this.y = y;
}
}
// function to perform BFS from a given node and mark all visited nodes
function bfs(forest, start, visited) {
// create a queue for BFS
let q = [];
q.push(start);
visited[start.x][start.y] = true;
// BFS loop
while (q.length > 0) {
let curr = q.shift();
// add unvisited neighboring nodes to the queue
let dx = [-1, 0, 1, 0];
let dy = [0, 1, 0, -1];
for (let i = 0; i < 4; i++) {
let nx = curr.x + dx[i];
let ny = curr.y + dy[i];
if (nx >= 0 && nx < forest.length && ny >= 0 && ny < forest[0].length && forest[nx][ny] == 1 && !visited[nx][ny]) {
q.push(new Node(nx, ny));
visited[nx][ny] = true;
}
}
}
}
// function to count the number of trees in a forest using BFS
function count_trees_in_forest(forest) {
let count = 0;
let n = forest.length;
let m = forest[0].length;
// create a 2D boolean array to keep track of visited nodes
let visited = new Array(n);
for (let i=0; i<n; i++) {
visited[i] = new Array(m).fill(false);
}
// iterate over all nodes in the forest and perform BFS from each unvisited tree
for (let i=0; i<n; i++) {
for (let j=0; j<m; j++) {
if (forest[i][j] == 1 && !visited[i][j]) {
bfs(forest,new Node(i,j),visited);
count++;
}
}
}
return count;
}
let forest=[
[0 ,1 ,1 ,0 ,0],
[0 ,0 ,0 ,0 ,0],
[0, 0, 0, 0, 0],
[0, 0, 0, 0, 1],
[0, 0, 0, 0, 0]];
let num_trees = count_trees_in_forest(forest);
console.log("The forest has " + num_trees + " trees.");
Output
The forest has 2 trees.
Time complexity : - O(NM)
Auxiliary Space :- O(MN)