Breadth First Search or BFS for a Graph
Last Updated :
23 Jul, 2025
Given a undirected graph represented by an adjacency list adj
, where each adj[i]
represents the list of vertices connected to vertex i
. Perform a Breadth First Search (BFS) traversal starting from vertex 0
, visiting vertices from left to right according to the adjacency list, and return a list containing the BFS traversal of the graph.
Examples:
Input: adj[][] = [[1,2], [0,2,3], [0,1,4], [1,4], [2,3]]
Output: [0, 1, 2, 3, 4]
Explanation: Starting from 0, the BFS traversal will follow these steps:
Visit 0 → Output: [0]
Visit 1 (first neighbor of 0) → Output: [0, 1]
Visit 2 (next neighbor of 0) → Output: [0, 1, 2]
Visit 3 (next neighbor of 1) → Output: [0, 1, 2, 3]
Visit 4 (neighbor of 2) → Final Output: [0, 1, 2, 3, 4]
Input: adj[][] = [[1, 2], [0, 2], [0, 1, 3, 4], [2], [2]]
Output: [0, 1, 2, 3, 4]
Explanation: Starting from 0, the BFS traversal proceeds as follows:
Visit 0 → Output: [0]
Visit 1 (the first neighbor of 0) → Output: [0, 1]
Visit 2 (the next neighbor of 0) → Output: [0, 1, 2]
Visit 3 (the first neighbor of 2 that hasn't been visited yet) → Output: [0, 1, 2, 3]
Visit 4 (the next neighbor of 2) → Final Output: [0, 1, 2, 3, 4]
What is Breadth First Search?
Breadth First Search (BFS) is a fundamental graph traversal algorithm. It begins with a node, then first traverses all its adjacent nodes. Once all adjacent are visited, then their adjacent are traversed.
- BFS is different from DFS in a way that closest vertices are visited before others. We mainly traverse vertices level by level.
- Popular graph algorithms like Dijkstra's shortest path, Kahn's Algorithm, and Prim's algorithm are based on BFS.
- BFS itself can be used to detect cycle in a directed and undirected graph, find shortest path in an unweighted graph and many more problems.
BFS from a Given Source
The algorithm starts from a given source and explores all reachable vertices from the given source. It is similar to the Breadth-First Traversal of a tree. Like tree, we begin with the given source (in tree, we begin with root) and traverse vertices level by level using a queue data structure. The only catch here is that, unlike trees, graphs may contain cycles, so we may come to the same node again. To avoid processing a node more than once, we use a Boolean visited array.
Follow the below given approach:
- Initialization: Enqueue the given source vertex into a queue and mark it as visited.
- Exploration: While the queue is not empty:
- Dequeue a node from the queue and visit it (e.g., print its value).
- For each unvisited neighbor of the dequeued node:
- Enqueue the neighbor into the queue.
- Mark the neighbor as visited.
- Termination: Repeat step 2 until the queue is empty.
This algorithm ensures that all nodes in the graph are visited in a breadth-first manner, starting from the starting node.
C++
#include<bits/stdc++.h>
using namespace std;
// BFS from given source s
vector<int> bfs(vector<vector<int>>& adj) {
int V = adj.size();
int s = 0; // source node
// create an array to store the traversal
vector<int> res;
// Create a queue for BFS
queue<int> q;
// Initially mark all the vertices as not visited
vector<bool> visited(V, false);
// Mark source node as visited and enqueue it
visited[s] = true;
q.push(s);
// Iterate over the queue
while (!q.empty()) {
// Dequeue a vertex from queue and store it
int curr = q.front();
q.pop();
res.push_back(curr);
// Get all adjacent vertices of the dequeued
// vertex curr If an adjacent has not been
// visited, mark it visited and enqueue it
for (int x : adj[curr]) {
if (!visited[x]) {
visited[x] = true;
q.push(x);
}
}
}
return res;
}
int main() {
vector<vector<int>> adj = {{1,2}, {0,2,3}, {0,4}, {1,4}, {2,3}};
vector<int> ans = bfs(adj);
for(auto i:ans) {
cout<<i<<" ";
}
return 0;
}
Java
// Function to find BFS of Graph from given source s
import java.util.*;
class GfG {
// BFS from given source s
static ArrayList<Integer> bfs(
ArrayList<ArrayList<Integer>> adj) {
int V = adj.size();
int s = 0; // source node
// create an array to store the traversal
ArrayList<Integer> res = new ArrayList<>();
// Create a queue for BFS
Queue<Integer> q = new LinkedList<>();
// Initially mark all the vertices as not visited
boolean[] visited = new boolean[V];
// Mark source node as visited and enqueue it
visited[s] = true;
q.add(s);
// Iterate over the queue
while (!q.isEmpty()) {
// Dequeue a vertex from queue and store it
int curr = q.poll();
res.add(curr);
// Get all adjacent vertices of the dequeued
// vertex curr If an adjacent has not been
// visited, mark it visited and enqueue it
for (int x : adj.get(curr)) {
if (!visited[x]) {
visited[x] = true;
q.add(x);
}
}
}
return res;
}
public static void main(String[] args) {
// create the adjacency list
// { {2, 3, 1}, {0}, {0, 4}, {0}, {2} }
ArrayList<ArrayList<Integer>> adj = new ArrayList<>();
adj.add(new ArrayList<>(Arrays.asList(1, 2)));
adj.add(new ArrayList<>(Arrays.asList(0, 2, 3)));
adj.add(new ArrayList<>(Arrays.asList(0, 4)));
adj.add(new ArrayList<>(Arrays.asList(1,4)));
adj.add(new ArrayList<>(Arrays.asList(2,3)));
ArrayList<Integer> ans = bfs(adj);
for (int i : ans) {
System.out.print(i + " ");
}
}
}
Python
# Function to find BFS of Graph from given source s
def bfs(adj):
# get number of vertices
V = len(adj)
# create an array to store the traversal
res = []
s = 0
# Create a queue for BFS
from collections import deque
q = deque()
# Initially mark all the vertices as not visited
visited = [False] * V
# Mark source node as visited and enqueue it
visited[s] = True
q.append(s)
# Iterate over the queue
while q:
# Dequeue a vertex from queue and store it
curr = q.popleft()
res.append(curr)
# Get all adjacent vertices of the dequeued
# vertex curr If an adjacent has not been
# visited, mark it visited and enqueue it
for x in adj[curr]:
if not visited[x]:
visited[x] = True
q.append(x)
return res
if __name__ == "__main__":
# create the adjacency list
# [ [2, 3, 1], [0], [0, 4], [0], [2] ]
adj = [[1,2], [0,2,3], [0,4], [1,4], [2,3]]
ans = bfs(adj)
for i in ans:
print(i, end=" ")
C#
// Function to find BFS of Graph from given source s
using System;
using System.Collections.Generic;
class GfG {
// BFS from given source s
static List<int> bfs(List<int>[] adj) {
int V = adj.Length;
int s = 0; // source node
// create an array to store the traversal
List<int> res = new List<int>();
// Create a queue for BFS
Queue<int> q = new Queue<int>();
// Initially mark all the vertices as not visited
bool[] visited = new bool[V];
// Mark source node as visited and enqueue it
visited[s] = true;
q.Enqueue(s);
// Iterate over the queue
while (q.Count > 0) {
// Dequeue a vertex from queue and store it
int curr = q.Dequeue();
res.Add(curr);
// Get all adjacent vertices of the dequeued
// vertex curr If an adjacent has not been
// visited, mark it visited and enqueue it
foreach (int x in adj[curr]) {
if (!visited[x]) {
visited[x] = true;
q.Enqueue(x);
}
}
}
return res;
}
static void Main() {
// create the adjacency list
// { {2, 3, 1}, {0}, {0, 4}, {0}, {2} }
List<int>[] adj = new List<int>[5];
adj[0] = new List<int> { 1, 2 };
adj[1] = new List<int> { 0, 2, 3 };
adj[2] = new List<int> { 0, 4 };
adj[3] = new List<int> { 1, 4 };
adj[4] = new List<int> { 2, 3 };
List<int> ans = bfs(adj);
foreach (int i in ans) {
Console.Write(i + " ");
}
}
}
JavaScript
// Function to find BFS of Graph from given source s
function bfs(adj) {
let V = adj.length;
let s = 0; // source node is 0
// create an array to store the traversal
let res = [];
// Create a queue for BFS
let q = [];
// Initially mark all the vertices as not visited
let visited = new Array(V).fill(false);
// Mark source node as visited and enqueue it
visited[s] = true;
q.push(s);
// Iterate over the queue
while (q.length > 0) {
// Dequeue a vertex from queue and store it
let curr = q.shift();
res.push(curr);
// Get all adjacent vertices of the dequeued
// vertex curr If an adjacent has not been
// visited, mark it visited and enqueue it
for (let x of adj[curr]) {
if (!visited[x]) {
visited[x] = true;
q.push(x);
}
}
}
return res;
}
// Main execution
let adj =
[ [1,2], [0,2,3], [0,4], [1,4], [2,3]];
let src = 0;
let ans = bfs(adj);
for (let i of ans) {
process.stdout.write(i + " ");
}
BFS of the Disconnected Graph
The above implementation takes a source as an input and prints only those vertices that are reachable from the source and would not print all vertices in case of disconnected graph. Let us see the algorithm that prints all vertices without any source and the graph maybe disconnected.
The algorithm is simple, instead of calling BFS for a single vertex, we call the above implemented BFS for all not yet visited vertices one by one.
C++
#include<bits/stdc++.h>
using namespace std;
// BFS from given source s
void bfs(vector<vector<int>>& adj, int s,
vector<bool>& visited, vector<int> &res) {
// Create a queue for BFS
queue<int> q;
// Mark source node as visited and enqueue it
visited[s] = true;
q.push(s);
// Iterate over the queue
while (!q.empty()) {
// Dequeue a vertex and store it
int curr = q.front();
q.pop();
res.push_back(curr);
// Get all adjacent vertices of the dequeued
// vertex curr If an adjacent has not been
// visited, mark it visited and enqueue it
for (int x : adj[curr]) {
if (!visited[x]) {
visited[x] = true;
q.push(x);
}
}
}
}
// Perform BFS for the entire graph which maybe
// disconnected
vector<int> bfsDisconnected(vector<vector<int>>& adj) {
int V = adj.size();
// create an array to store the traversal
vector<int> res;
// Initially mark all the vertices as not visited
vector<bool> visited(V, false);
// perform BFS for each node
for (int i = 0; i < adj.size(); ++i) {
if (!visited[i]) {
bfs(adj, i, visited, res);
}
}
return res;
}
int main() {
vector<vector<int>> adj = { {1, 2}, {0}, {0},
{4}, {3, 5}, {4}};
vector<int> ans = bfsDisconnected(adj);
for(auto i:ans) {
cout<<i<<" ";
}
return 0;
}
Java
// BFS from given source s
import java.util.*;
class GfG {
// BFS from given source s
static ArrayList<Integer>
bfsOfGraph(ArrayList<ArrayList<Integer>> adj,
int s, boolean[] visited, ArrayList<Integer> res) {
// Create a queue for BFS
Queue<Integer> q = new LinkedList<>();
// Mark source node as visited and enqueue it
visited[s] = true;
q.add(s);
// Iterate over the queue
while (!q.isEmpty()) {
// Dequeue a vertex and store it
int curr = q.poll();
res.add(curr);
// Get all adjacent vertices of the dequeued
// vertex curr If an adjacent has not been
// visited, mark it visited and enqueue it
for (int x : adj.get(curr)) {
if (!visited[x]) {
visited[x] = true;
q.add(x);
}
}
}
return res;
}
// Perform BFS for the entire graph which maybe
// disconnected
static ArrayList<Integer> bfsDisconnected(
ArrayList<ArrayList<Integer>> adj) {
int V = adj.size();
// create an array to store the traversal
ArrayList<Integer> res = new ArrayList<>();
// Initially mark all the vertices as not visited
boolean[] visited = new boolean[V];
// perform BFS for each node
for (int i = 0; i < V; i++) {
if (!visited[i]) {
bfsOfGraph(adj, i, visited, res);
}
}
return res;
}
public static void main(String[] args) {
ArrayList<ArrayList<Integer>> adj = new ArrayList<>();
adj.add(new ArrayList<>(Arrays.asList(1, 2)));
adj.add(new ArrayList<>(Arrays.asList(0)));
adj.add(new ArrayList<>(Arrays.asList(0)));
adj.add(new ArrayList<>(Arrays.asList(4)));
adj.add(new ArrayList<>(Arrays.asList(3, 5)));
adj.add(new ArrayList<>(Arrays.asList(4)));
int src = 0;
ArrayList<Integer> ans = bfsDisconnected(adj);
for (int i : ans) {
System.out.print(i + " ");
}
}
}
Python
# BFS from given source s
from collections import deque
def bfsOfGraph(adj, s, visited, res):
# Create a queue for BFS
q = deque()
# Mark source node as visited and enqueue it
visited[s] = True
q.append(s)
# Iterate over the queue
while q:
# Dequeue a vertex and store it
curr = q.popleft()
res.append(curr)
# Get all adjacent vertices of the dequeued
# vertex curr If an adjacent has not been
# visited, mark it visited and enqueue it
for x in adj[curr]:
if not visited[x]:
visited[x] = True
q.append(x)
return res
# Perform BFS for the entire graph which maybe
# disconnected
def bfsDisconnected(adj):
V = len(adj)
# create an array to store the traversal
res = []
# Initially mark all the vertices as not visited
visited = [False] * V
# perform BFS for each node
for i in range(V):
if not visited[i]:
bfsOfGraph(adj, i, visited, res)
return res
if __name__ == "__main__":
adj = [[1, 2], [0], [0],
[4], [3, 5], [4]]
ans = bfsDisconnected(adj)
for i in ans:
print(i, end=" ")
C#
// BFS from given source s
using System;
using System.Collections.Generic;
class GfG {
// BFS from given source s
static List<int> bfsOfGraph(List<int>[] adj,
int s, bool[] visited, List<int> res) {
// Create a queue for BFS
Queue<int> q = new Queue<int>();
// Mark source node as visited and enqueue it
visited[s] = true;
q.Enqueue(s);
// Iterate over the queue
while (q.Count > 0) {
// Dequeue a vertex and store it
int curr = q.Dequeue();
res.Add(curr);
// Get all adjacent vertices of the dequeued
// vertex curr If an adjacent has not been
// visited, mark it visited and enqueue it
foreach (int x in adj[curr]) {
if (!visited[x]) {
visited[x] = true;
q.Enqueue(x);
}
}
}
return res;
}
// Perform BFS for the entire graph which maybe
// disconnected
static List<int> bfsDisconnected(List<int>[] adj) {
int V = adj.Length;
// create an array to store the traversal
List<int> res = new List<int>();
// Initially mark all the vertices as not visited
bool[] visited = new bool[V];
// perform BFS for each node
for (int i = 0; i < V; i++) {
if (!visited[i]) {
bfsOfGraph(adj, i, visited, res);
}
}
return res;
}
static void Main() {
List<int>[] adj = new List<int>[6];
adj[0] = new List<int> { 1, 2 };
adj[1] = new List<int> { 0 };
adj[2] = new List<int> { 0 };
adj[3] = new List<int> { 4 };
adj[4] = new List<int> { 3, 5 };
adj[5] = new List<int> { 4 };
List<int> ans = bfsDisconnected(adj);
foreach (int i in ans) {
Console.Write(i + " ");
}
}
}
JavaScript
// BFS from given source s
function bfsOfGraph(adj, s, visited, res) {
// Create a queue for BFS
let q = [];
// Mark source node as visited and enqueue it
visited[s] = true;
q.push(s);
// Iterate over the queue
while (q.length > 0) {
// Dequeue a vertex and store it
let curr = q.shift();
res.push(curr);
// Get all adjacent vertices of the dequeued
// vertex curr If an adjacent has not been
// visited, mark it visited and enqueue it
for (let x of adj[curr]) {
if (!visited[x]) {
visited[x] = true;
q.push(x);
}
}
}
return res;
}
// Perform BFS for the entire graph which maybe
// disconnected
function bfsDisconnected(adj) {
let V = adj.length;
// create an array to store the traversal
let res = [];
// Initially mark all the vertices as not visited
let visited = new Array(V).fill(false);
// perform BFS for each node
for (let i = 0; i < V; i++) {
if (!visited[i]) {
bfsOfGraph(adj, i, visited, res);
}
}
return res;
}
// Main execution
let adj =
[[1, 2], [0], [0],
[4], [3, 5], [4]];
let ans = bfsDisconnected(adj);
for (let i of ans) {
process.stdout.write(i + " ");
}
Complexity Analysis of Breadth-First Search (BFS) Algorithm
Time Complexity: O(V + E), BFS explores all the vertices and edges in the graph. In the worst case, it visits every vertex and edge once. Therefore, the time complexity of BFS is O(V + E), where V and E are the number of vertices and edges in the given graph.
Auxiliary Space: O(V), BFS uses a queue to keep track of the vertices that need to be visited. In the worst case, the queue can contain all the vertices in the graph. Therefore, the space complexity of BFS is O(V).
Applications of BFS in Graphs
BFS has various applications in graph theory and computer science, including:
- Shortest Path Finding: BFS can be used to find the shortest path between two nodes in an unweighted graph. By keeping track of the parent of each node during the traversal, the shortest path can be reconstructed.
- Cycle Detection: BFS can be used to detect cycles in a graph. If a node is visited twice during the traversal, it indicates the presence of a cycle.
- Connected Components: BFS can be used to identify connected components in a graph. Each connected component is a set of nodes that can be reached from each other.
- Topological Sorting: BFS can be used to perform topological sorting on a directed acyclic graph (DAG). Topological sorting arranges the nodes in a linear order such that for any edge (u, v), u appears before v in the order.
- Level Order Traversal of Binary Trees: BFS can be used to perform a level order traversal of a binary tree. This traversal visits all nodes at the same level before moving to the next level.
- Network Routing: BFS can be used to find the shortest path between two nodes in a network, making it useful for routing data packets in network protocols.
Problems on BFS for a Graph
FAQs on Breadth First Search (BFS) for a Graph
Question 1: What is BFS and how does it work?
Answer: BFS is a graph traversal algorithm that systematically explores a graph by visiting all the vertices at a given level before moving on to the next level. It starts from a starting vertex, enqueues it into a queue, and marks it as visited. Then, it dequeues a vertex from the queue, visits it, and enqueues all its unvisited neighbors into the queue. This process continues until the queue is empty.
Question 2: What are the applications of BFS?
Answer: BFS has various applications, including finding the shortest path in an unweighted graph, detecting cycles in a graph, topologically sorting a directed acyclic graph (DAG), finding connected components in a graph, and solving puzzles like mazes and Sudoku.
Question 3: What is the time complexity of BFS?
Answer: The time complexity of BFS is O(V + E), where V is the number of vertices and E is the number of edges in the graph.
Question 4: What is the space complexity of BFS?
Answer: The space complexity of BFS is O(V), as it uses a queue to keep track of the vertices that need to be visited.
Question 5: What are the advantages of using BFS?
Answer: BFS is simple to implement and efficient for finding the shortest path in an unweighted graph. It also guarantees that all the vertices in the graph are visited.
Related Articles:
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