Longest balanced binary substring with equal count of 1s and 0s
Last Updated :
06 Dec, 2021
Given a binary string str[] of size N. The task is to find the longest balanced substring. A substring is balanced if it contains an equal number of 0 and 1.
Examples:
Input: str = “110101010”
Output: 10101010
Explanation: The formed substring contain equal count of 1 and 0 i.e, count of 1 and 0 is same equal to 4.
Input: str = “0000”
Output: -1
Naive Approach: A simple solution is to use two nested loops to generate every substring. And a third loop to count a number of 0s and 1s in the current substring. Then print the longest substring among them.
Time Complexity: O(N^3)
Auxiliary Space: O(1)
Efficient solution: With the help of precomputation, store the difference between the count of 0s and the count of 1s from start till current index. This difference can then be used to determine the longest substring with equal 0s and 1s, as the longest distance between any duplicate values in the difference array. Use a Map-based hashing to do precomputation. Follow the steps below to solve the problem:
- Initialize the map<int, int> m[].
- Set the value of m[0] as -1.
- Initialize the variables count_0, count_1, res, start and end.
- Traverse the string str[] using the variable i and perform the following tasks:
- Keep the track of counts of 1s and 0s as count_1 and count_0 respectively.
- See if the current difference between count_1 and count_0 is already there in the map m[] or not. If yes, then perform the following tasks:
- The substring from the previous appearance and current index has same number of 0s and 1s.
- If the current found substring’s length is greater than res then set the found substring as the answer so far.
- If it is appearing for the first time, store the current difference and the current index in the map i.e, m[count_1 – count_0] equals i.
- If count_0 and count_1 are both 0, then print -1.
- Otherwise, print the substring from start to end.
Below is the implementation of the above approach.
C++
#include <bits/stdc++.h>
using namespace std;
string stringLen(string str)
{
map< int , int > m;
m[0] = -1;
int count_0 = 0, count_1 = 0;
int start, end, res = 0;
for ( int i = 0; i < str.size(); i++) {
if (str[i] == '0' )
count_0++;
else
count_1++;
if (m.find(count_1 - count_0) != m.end()) {
if ((i - m[count_1 - count_0]) > res) {
start = m.find(
count_1 - count_0)
->second;
end = i;
res = end - start;
}
}
else
m[count_1 - count_0] = i;
}
if (count_0 == 0 || count_1 == 0)
return "-1" ;
return str.substr(start + 1, end + 1);
}
int main()
{
string str = "110101010" ;
cout << stringLen(str);
return 0;
}
|
Java
import java.io.*;
class GFG
{
static String stringLen(String str)
{
int [] m = new int [ 100000 ];
m[ 0 ] = - 1 ;
int count_0 = 0 ; int count_1 = 0 ;
int start = 0 ; int end = 0 ; int res = 0 ;
for ( int i = 0 ; i < str.length(); i++) {
if (str.charAt(i) == '0' )
count_0++;
else
count_1++;
if (m[count_1 - count_0]!= 0 ) {
if ((i - m[count_1 - count_0]) > res) {
start = m[count_1 - count_0];
end = i;
res = end - start;
}
}
else
m[count_1 - count_0] = i;
}
if (count_0 == 0 || count_1 == 0 )
return "-1" ;
return str.substring(start , end + 2 );
}
public static void main (String[] args)
{
String str = "110101010" ;
System.out.println(stringLen(str));
}
}
|
Python3
def stringLen ( str ) :
m = {}
m[ 0 ] = - 1
count_0 = 0
count_1 = 0
res = 0
for i in range ( len ( str )):
if ( str [i] = = '0' ):
count_0 + = 1
else :
count_1 + = 1
if ((count_1 - count_0) in m):
if ((i - m[count_1 - count_0]) > res):
start = m[(count_1 - count_0)]
end = i
res = end - start
else :
m[count_1 - count_0] = i
if (count_0 = = 0 or count_1 = = 0 ):
return "-1"
return str [start + 1 : start + 1 + end + 1 ]
str = "110101010"
print (stringLen( str ))
|
C#
using System;
using System.Collections;
using System.Collections.Generic;
class GFG
{
static string stringLen( string str)
{
int []m = new int [100000];
m[0] = -1;
int count_0 = 0; int count_1 = 0;
int start = 0; int end = 0; int res = 0;
for ( int i = 0; i < str.Length; i++) {
if (str[i] == '0' )
count_0++;
else
count_1++;
if (m[count_1 - count_0]!= 0) {
if ((i - m[count_1 - count_0]) > res) {
start = m[count_1 - count_0];
end = i;
res = end - start;
}
}
else
m[count_1 - count_0] = i;
}
if (count_0 == 0 || count_1 == 0)
return "-1" ;
return str.Substring(start, end - start + 2);
}
public static void Main ()
{
string str = "110101010" ;
Console.Write(stringLen(str));
}
}
|
Javascript
<script>
const stringLen = (str) => {
let m = {};
m[0] = -1;
let count_0 = 0, count_1 = 0;
let start, end, res = 0;
for (let i = 0; i < str.length; i++) {
if (str[i] == '0' )
count_0++;
else
count_1++;
if ((count_1 - count_0) in m) {
if ((i - m[count_1 - count_0]) > res) {
start = m[(count_1 - count_0)];
end = i;
res = end - start;
}
}
else
m[count_1 - count_0] = i;
}
if (count_0 == 0 || count_1 == 0)
return "-1" ;
return str.substring(start + 1, start + 1 + end + 1);
}
let str = "110101010" ;
document.write(stringLen(str));
</script>
|
Time Complexity: O(N)
Auxiliary Space: O(N)
Like Article
Suggest improvement
Share your thoughts in the comments
Please Login to comment...