# Finding minimum vertex cover size of a graph using binary search

A vertex cover of an undirected graph is a subset of its vertices such that for every edge (u, v) of the graph, either ‘u’ or ‘v’ is in vertex cover. There may be a lot of vertex covers possible for a graph.

**Problem** Find the size of the minimum size vertex cover, that is, cardinality of a vertex cover with minimum cardinality, for an undirected connected graph with V vertices and m edges.

**Examples:**

Input: V = 6, E = 6 6 / / 1 -----5 /|\ 3 | \ \ | \ 2 4 Output: Minimum vertex cover size = 2 Consider subset of vertices {1, 2}, every edge in above graph is either incident on vertex 1 or 2. Hence the minimum vertex cover = {1, 2}, the size of which is 2. Input: V = 6, E = 7 2 ---- 4 ---- 6 /| | 1 | | \| | 3 ---- 5 Output: Minimum vertex cover size = 3 Consider subset of vertices {2, 3, 4}, every edge in above graph is either incident on vertex 2, 3 or 4. Hence the minimum size of a vertex cover can be 3.

**Method 1 (Naive)**

We can check in O(E + V) time if a given subset of vertices is a vertex cover or not, using the following algorithm.

Generate all 2^{V}subsets of vertices in graph and do following for every subset. 1. edges_covered = 0 2. for each vertex in current subset 3. for all edges emerging out of current vertex 4. if the edge is not already marked visited 5. mark the edge visited 6. edges_covered++ 7. if edges_covered is equal to total number edges 8. return size of current subset

An upper bound on time complexity of this solution is O((E + V) * 2^{V})

**Method 2 (Binary Search)**

If we generate 2^{V} subsets first by generating ^{V}C_{V} subsets, then ^{V}C_{(V-1)} subsets, and so on upto ^{V}C_{0} subsets(2^{V} = ^{V}C_{V} + ^{V}C_{(V-1)} + … + ^{V}C_{1} + ^{V}C_{0}). Our objective is now to find the minimum k such that at least one subset of size ‘k’ amongst ^{V}C_{k} subsets is a vertex cover [ We know that if minimum size vertex cover is of size k, then there will exist a vertex cover of all sizes more than k. That is, there will be a vertex cover of size k + 1, k + 2, k + 3, …, n. ]

Now let’s imagine a boolean array of size n and call it isCover[]. So if the answer of the question; “Does a vertex cover of size x exist?” is yes, we put a ‘1’ at xth position, otherwise ‘0’.

The array isCover[] will look like:

1 | 2 | 3 | . | . | . | k | . | . | . | n |

0 | 0 | 0 | . | . | . | 1 | . | . | . | 1 |

The array is sorted and hence binary searchable, as no index before **k** will have a ‘1’, and every index after **k**(inclusive) will have a ‘1’, so **k** is the answer.

So we can apply Binary Search to find the minimum size vertex set that covers all edges (this problem is equivalent to finding last 1 in isCover[]). Now the problem is how to generate all subsets of a given size. The idea is to use Gosper’s hack.

**What is Gosper’s Hack?**

Gosper’s hack is a technique to get the next number with same number of bits set. So we set the first x bits from right and generate next number with x bits set until the number is less than 2^{V}. In this way, we can generate all ^{V}Cx numbers with x bits set.

`int` `set = (1 << k) - 1; ` `int` `limit = (1 << V); ` `while` `(set < limit) ` `{ ` ` ` `// Do your stuff with current set ` ` ` `doStuff(set); ` ` ` ` ` `// Gosper's hack: ` ` ` `int` `c = set & -set; ` ` ` `int` `r = set + c; ` ` ` `set = (((r^set) >>> 2) / c) | r; ` `} ` |

*chevron_right*

*filter_none*

Source : StackExchange

We use gosper’s hack to generate all subsets of size x(0 < x <= V), that is, to check whether we have a '1' or '0' at any index x in isCover[] array.

## C++

`// A C++ program to find size of minimum vertex ` `// cover using Binary Search ` `#include<bits/stdc++.h> ` `#define maxn 25 ` ` ` `using` `namespace` `std; ` ` ` `// Global array to store the graph ` `// Note: since the array is global, all the ` `// elements are 0 initially ` `bool` `gr[maxn][maxn]; ` ` ` `// Returns true if there is a possible subset ` `// of size 'k' that can be a vertex cover ` `bool` `isCover(` `int` `V, ` `int` `k, ` `int` `E) ` `{ ` ` ` `// Set has first 'k' bits high initially ` ` ` `int` `set = (1 << k) - 1; ` ` ` ` ` `int` `limit = (1 << V); ` ` ` ` ` `// to mark the edges covered in each subset ` ` ` `// of size 'k' ` ` ` `bool` `vis[maxn][maxn]; ` ` ` ` ` `while` `(set < limit) ` ` ` `{ ` ` ` `// Reset visited array for every subset ` ` ` `// of vertices ` ` ` `memset` `(vis, 0, ` `sizeof` `vis); ` ` ` ` ` `// set counter for number of edges covered ` ` ` `// from this subset of vertices to zero ` ` ` `int` `cnt = 0; ` ` ` ` ` `// selected vertex cover is the the indices ` ` ` `// where 'set' has its bit high ` ` ` `for` `(` `int` `j = 1, v = 1 ; j < limit ; j = j << 1, v++) ` ` ` `{ ` ` ` `if` `(set & j) ` ` ` `{ ` ` ` `// Mark all edges emerging out of this ` ` ` `// vertex visited ` ` ` `for` `(` `int` `k = 1 ; k <= V ; k++) ` ` ` `{ ` ` ` `if` `(gr[v][k] && !vis[v][k]) ` ` ` `{ ` ` ` `vis[v][k] = 1; ` ` ` `vis[k][v] = 1; ` ` ` `cnt++; ` ` ` `} ` ` ` `} ` ` ` `} ` ` ` `} ` ` ` ` ` `// If the current subset covers all the edges ` ` ` `if` `(cnt == E) ` ` ` `return` `true` `; ` ` ` ` ` `// Generate previous combination with k bits high ` ` ` `// set & -set = (1 << last bit high in set) ` ` ` `int` `c = set & -set; ` ` ` `int` `r = set + c; ` ` ` `set = (((r^set) >> 2) / c) | r; ` ` ` `} ` ` ` `return` `false` `; ` `} ` ` ` `// Returns answer to graph stored in gr[][] ` `int` `findMinCover(` `int` `n, ` `int` `m) ` `{ ` ` ` `// Binary search the answer ` ` ` `int` `left = 1, right = n; ` ` ` `while` `(right > left) ` ` ` `{ ` ` ` `int` `mid = (left + right) >> 1; ` ` ` `if` `(isCover(n, mid, m) == ` `false` `) ` ` ` `left = mid + 1; ` ` ` `else` ` ` `right = mid; ` ` ` `} ` ` ` ` ` `// at the end of while loop both left and ` ` ` `// right will be equal,/ as when they are ` ` ` `// not, the while loop won't exit the minimum ` ` ` `// size vertex cover = left = right ` ` ` `return` `left; ` `} ` ` ` `// Inserts an edge in the graph ` `void` `insertEdge(` `int` `u, ` `int` `v) ` `{ ` ` ` `gr[u][v] = 1; ` ` ` `gr[v][u] = 1; ` `// Undirected graph ` `} ` ` ` `// Driver code ` `int` `main() ` `{ ` ` ` `/* ` ` ` `6 ` ` ` `/ ` ` ` `1 ----- 5 vertex cover = {1, 2} ` ` ` `/|\ ` ` ` `3 | \ ` ` ` `\ | \ ` ` ` `2 4 */` ` ` `int` `V = 6, E = 6; ` ` ` `insertEdge(1, 2); ` ` ` `insertEdge(2, 3); ` ` ` `insertEdge(1, 3); ` ` ` `insertEdge(1, 4); ` ` ` `insertEdge(1, 5); ` ` ` `insertEdge(1, 6); ` ` ` `cout << ` `"Minimum size of a vertex cover = "` ` ` `<< findMinCover(V, E) << endl; ` ` ` ` ` ` ` `// Let us create another graph ` ` ` `memset` `(gr, 0, ` `sizeof` `gr); ` ` ` `/* ` ` ` `2 ---- 4 ---- 6 ` ` ` `/| | ` ` ` `1 | | vertex cover = {2, 3, 4} ` ` ` `\ | | ` ` ` `3 ---- 5 */` ` ` ` ` `V = 6, E = 7; ` ` ` `insertEdge(1, 2); ` ` ` `insertEdge(1, 3); ` ` ` `insertEdge(2, 3); ` ` ` `insertEdge(2, 4); ` ` ` `insertEdge(3, 5); ` ` ` `insertEdge(4, 5); ` ` ` `insertEdge(4, 6); ` ` ` `cout << ` `"Minimum size of a vertex cover = "` ` ` `<< findMinCover(V, E) << endl; ` ` ` ` ` `return` `0; ` `} ` |

*chevron_right*

*filter_none*

## Python3

`# A Python3 program to find size of minimum ` `# vertex cover using Binary Search ` ` ` `# Returns true if there is a possible subSet ` `# of size 'k' that can be a vertex cover ` `def` `isCover(V, k, E): ` ` ` ` ` `# Set has first 'k' bits high initially ` ` ` `Set` `=` `(` `1` `<< k) ` `-` `1` ` ` ` ` `limit ` `=` `(` `1` `<< V) ` ` ` ` ` `# to mark the edges covered in each ` ` ` `# subSet of size 'k' ` ` ` `vis ` `=` `[[` `None` `] ` `*` `maxn ` `for` `i ` `in` `range` `(maxn)] ` ` ` ` ` `while` `(` `Set` `< limit): ` ` ` ` ` `# ReSet visited array for every ` ` ` `# subSet of vertices ` ` ` `vis ` `=` `[[` `0` `] ` `*` `maxn ` `for` `i ` `in` `range` `(maxn)] ` ` ` ` ` `# Set counter for number of edges covered ` ` ` `# from this subSet of vertices to zero ` ` ` `cnt ` `=` `0` ` ` ` ` `# selected vertex cover is the the ` ` ` `# indices where 'Set' has its bit high ` ` ` `j ` `=` `1` ` ` `v ` `=` `1` ` ` `while` `(j < limit): ` ` ` `if` `(` `Set` `& j): ` ` ` ` ` `# Mark all edges emerging out of ` ` ` `# this vertex visited ` ` ` `for` `k ` `in` `range` `(` `1` `, V ` `+` `1` `): ` ` ` `if` `(gr[v][k] ` `and` `not` `vis[v][k]): ` ` ` `vis[v][k] ` `=` `1` ` ` `vis[k][v] ` `=` `1` ` ` `cnt ` `+` `=` `1` ` ` `j ` `=` `j << ` `1` ` ` `v ` `+` `=` `1` ` ` ` ` `# If the current subSet covers all the edges ` ` ` `if` `(cnt ` `=` `=` `E): ` ` ` `return` `True` ` ` ` ` `# Generate previous combination with k bits high ` ` ` `# Set & -Set = (1 << last bit high in Set) ` ` ` `c ` `=` `Set` `& ` `-` `Set` ` ` `r ` `=` `Set` `+` `c ` ` ` `Set` `=` `(((r ^ ` `Set` `) >> ` `2` `) ` `/` `/` `c) | r ` ` ` `return` `False` ` ` `# Returns answer to graph stored in gr[][] ` `def` `findMinCover(n, m): ` ` ` ` ` `# Binary search the answer ` ` ` `left ` `=` `1` ` ` `right ` `=` `n ` ` ` `while` `(right > left): ` ` ` `mid ` `=` `(left ` `+` `right) >> ` `1` ` ` `if` `(isCover(n, mid, m) ` `=` `=` `False` `): ` ` ` `left ` `=` `mid ` `+` `1` ` ` `else` `: ` ` ` `right ` `=` `mid ` ` ` ` ` `# at the end of while loop both left and ` ` ` `# right will be equal,/ as when they are ` ` ` `# not, the while loop won't exit the ` ` ` `# minimum size vertex cover = left = right ` ` ` `return` `left ` ` ` `# Inserts an edge in the graph ` `def` `insertEdge(u, v): ` ` ` `gr[u][v] ` `=` `1` ` ` `gr[v][u] ` `=` `1` `# Undirected graph ` ` ` `# Driver code ` `maxn ` `=` `25` ` ` `# Global array to store the graph ` `# Note: since the array is global, ` `# all the elements are 0 initially ` `gr ` `=` `[[` `None` `] ` `*` `maxn ` `for` `i ` `in` `range` `(maxn)] ` ` ` `# ` `# 6 ` `# / ` `# 1 ----- 5 vertex cover = {1, 2} ` `# /|\ ` `# 3 | \ ` `# \ | \ ` `# 2 4 ` `V ` `=` `6` `E ` `=` `6` `insertEdge(` `1` `, ` `2` `) ` `insertEdge(` `2` `, ` `3` `) ` `insertEdge(` `1` `, ` `3` `) ` `insertEdge(` `1` `, ` `4` `) ` `insertEdge(` `1` `, ` `5` `) ` `insertEdge(` `1` `, ` `6` `) ` `print` `(` `"Minimum size of a vertex cover = "` `, ` ` ` `findMinCover(V, E)) ` ` ` `# Let us create another graph ` `gr ` `=` `[[` `0` `] ` `*` `maxn ` `for` `i ` `in` `range` `(maxn)] ` ` ` `# ` `# 2 ---- 4 ---- 6 ` `# /| | ` `# 1 | | vertex cover = {2, 3, 4} ` `# \ | | ` `# 3 ---- 5 ` `V ` `=` `6` `E ` `=` `7` `insertEdge(` `1` `, ` `2` `) ` `insertEdge(` `1` `, ` `3` `) ` `insertEdge(` `2` `, ` `3` `) ` `insertEdge(` `2` `, ` `4` `) ` `insertEdge(` `3` `, ` `5` `) ` `insertEdge(` `4` `, ` `5` `) ` `insertEdge(` `4` `, ` `6` `) ` `print` `(` `"Minimum size of a vertex cover = "` `, ` ` ` `findMinCover(V, E)) ` ` ` `# This code is contributed by PranchalK ` |

*chevron_right*

*filter_none*

**Output:**

Minimum size of a vertex cover = 2 Minimum size of a vertex cover = 3

**Conclusion:**

Time Complexity : **O (E * ( ^{V}C_{V/2} + ^{V}C_{V/4} + ^{V}C_{V/8} +…upto ^{V}C_{k} ) )**

These terms are not more than log(V) in worst case.

**Note:** Gosper’s hack works for upto V = 31 only, if we take ‘long long int’ instead of ‘int’ it can work upto V = 63.

This article is contributed by **Saumye Malhotra ** .If you like GeeksforGeeks and would like to contribute, you can also write an article using contribute.geeksforgeeks.org or mail your article to contribute@geeksforgeeks.org. See your article appearing on the GeeksforGeeks main page and help other Geeks.

Please write comments if you find anything incorrect, or you want to share more information about the topic discussed above.

## Recommended Posts:

- Vertex Cover Problem | Set 1 (Introduction and Approximate Algorithm)
- Finding the path from one vertex to rest using BFS
- Find a Mother Vertex in a Graph
- Find the Degree of a Particular vertex in a Graph
- All vertex pairs connected with exactly k edges in a graph
- k'th heaviest adjacent node in a graph where each vertex has weight
- Topological Sort of a graph using departure time of vertex
- Program to Calculate the Edge Cover of a Graph
- Minimum swaps so that binary search can be applied
- Finding in and out degrees of all vertices in a graph
- Meta Binary Search | One-Sided Binary Search
- Breadth First Search or BFS for a Graph
- Depth First Search or DFS for a Graph
- Find if an undirected graph contains an independent set of a given size
- Linear Search vs Binary Search