Find numbers of balancing positions in string
Last Updated :
18 Sep, 2023
Given a string, the task is to find the number of such balancing positions in the string from where the left and the right part of that string contains the same characters. The frequency of characters doesn’t matter.
Examples:
Input : str[] = abaaba
Output : Number of balancing positions : 3
Explanations : All 3 balancing positions are as :
ab|aaba, aba|aba, abaa|ba
Input : str[] = noon
Output : Number of balancing positions : 1
Explanations : Balancing position is :
no|on
Naive Approach:
If we try to solve this problem by the naive approach, we have to process for all n positions of string and at each position, we must check whether the left and right parts of our string from that position have the same characters or not.
The process of finding whether the position is balancing or not (frequency of both parts need not be the same) can be done in O(n^2) time for a single position( where we should check if each element in the left part is present in right and vice-versa). This whole process will lead to an algorithm of time complexity O(n^3).
Efficient Approach:
The idea of an efficient algorithm came from this article. The main difference is that we should not care about equal frequency, and using traversing the string.
We first fill right[] with counts of all characters. Then we traverse the string from left to right. For every character, we increment its count in left[] and decrement count in right[]. For any point being traversed, if all characters that have a non-zero value in left also have a non-zero value in right, and vice versa is also true, then we increment the result.
Implementation:
C++
#include<bits/stdc++.h>
using namespace std;
const int MAX_CHAR = 256;
int countBalance( char *str)
{
int n = strlen (str);
int leftVisited[MAX_CHAR] = {0};
int rightVisited[MAX_CHAR] = {0};
for ( int i=0; i<n; i++)
rightVisited[str[i]]++;
int res = 0;
for ( int i=0; i<n; i++)
{
leftVisited[str[i]]++;
rightVisited[str[i]]--;
int j;
for (j=0; j<MAX_CHAR; j++)
{
if ( (leftVisited[j] == 0 &&
rightVisited[j] != 0) ||
(leftVisited[j] != 0 &&
rightVisited[j] == 0)
)
break ;
}
if (j == MAX_CHAR)
res++;
}
return res;
}
int main()
{
char str[] = "abaababa" ;
cout << countBalance(str);
return 0;
}
|
Java
class GFG
{
static final int MAX_CHAR = 256 ;
static int countBalance(String s)
{
char [] str=s.toCharArray();
int n = str.length;
int [] rightVisited = new int [MAX_CHAR];
int [] leftVisited = new int [MAX_CHAR];
for ( int i= 0 ; i<n; i++)
rightVisited[str[i]]++;
int res = 0 ;
for ( int i= 0 ; i<n; i++)
{
leftVisited[str[i]]++;
rightVisited[str[i]]--;
int j;
for (j= 0 ; j<MAX_CHAR; j++)
{
if ( (leftVisited[j] == 0 &&
rightVisited[j] != 0 ) ||
(leftVisited[j] != 0 &&
rightVisited[j] == 0 )
)
break ;
}
if (j == MAX_CHAR)
res++;
}
return res;
}
public static void main(String[] args)
{
String str = "abaababa" ;
System.out.println(countBalance(str));
}
}
|
Python3
MAX_CHAR = 256
def countBalance(string):
n = len (string)
leftVisited = [ 0 ] * (MAX_CHAR)
rightVisited = [ 0 ] * (MAX_CHAR)
for i in range ( 0 , n):
rightVisited[ ord (string[i])] + = 1
res = 0
for i in range ( 0 , n):
leftVisited[ ord (string[i])] + = 1
rightVisited[ ord (string[i])] - = 1
j = 0
while j < MAX_CHAR:
if ((leftVisited[j] = = 0 and
rightVisited[j] ! = 0 ) or
(leftVisited[j] ! = 0 and
rightVisited[j] = = 0 )):
break
j + = 1
if j = = MAX_CHAR:
res + = 1
return res
if __name__ = = "__main__" :
string = "abaababa"
print (countBalance(string))
|
C#
using System;
class GFG
{
static int MAX_CHAR = 256;
static int countBalance( string s)
{
int n = s.Length;
int [] rightVisited = new int [MAX_CHAR];
int [] leftVisited = new int [MAX_CHAR];
for ( int i = 0; i < n; i++)
rightVisited[s[i]]++;
int res = 0;
for ( int i = 0; i < n; i++)
{
leftVisited[s[i]]++;
rightVisited[s[i]]--;
int j;
for (j = 0; j < MAX_CHAR; j++)
{
if ((leftVisited[j] == 0 &&
rightVisited[j] != 0) ||
(leftVisited[j] != 0 &&
rightVisited[j] == 0))
break ;
}
if (j == MAX_CHAR)
res++;
}
return res;
}
public static void Main(String []args)
{
string str = "abaababa" ;
Console.WriteLine(countBalance(str));
}
}
|
PHP
<?php
$MAX_CHAR = 256;
function countBalance( $str )
{
global $MAX_CHAR ;
$n = strlen ( $str );
$leftVisited = array_fill (0, $MAX_CHAR , NULL);
$rightVisited = array_fill (0, $MAX_CHAR , NULL);
for ( $i = 0; $i < $n ; $i ++)
$rightVisited [ord( $str [ $i ])]++;
$res = 0;
for ( $i = 0; $i < $n ; $i ++)
{
$leftVisited [ord( $str [ $i ])]++;
$rightVisited [ord( $str [ $i ])]--;
for ( $j = 0; $j < $MAX_CHAR ; $j ++)
{
if (( $leftVisited [ $j ] == 0 &&
$rightVisited [ $j ] != 0) ||
( $leftVisited [ $j ] != 0 &&
$rightVisited [ $j ] == 0)
)
break ;
}
if ( $j == $MAX_CHAR )
$res ++;
}
return $res ;
}
$str = "abaababa" ;
echo countBalance( $str );
?>
|
Javascript
<script>
var MAX_CHAR = 256;
function countBalance(str)
{
var n = str.length;
var leftVisited = Array(MAX_CHAR).fill(0);
var rightVisited = Array(MAX_CHAR).fill(0);
for ( var i=0; i<n; i++)
rightVisited[str[i].charCodeAt(0)]++;
var res = 0;
for ( var i=0; i<n; i++)
{
leftVisited[str[i].charCodeAt(0)]++;
rightVisited[str[i].charCodeAt(0)]--;
var j;
for (j=0; j<MAX_CHAR; j++)
{
if ( (leftVisited[j] == 0 &&
rightVisited[j] != 0) ||
(leftVisited[j] != 0 &&
rightVisited[j] == 0)
)
break ;
}
if (j == MAX_CHAR)
res++;
}
return res;
}
var str = "abaababa" ;
document.write( countBalance(str));
</script>
|
Like Article
Suggest improvement
Share your thoughts in the comments
Please Login to comment...