Minimum sum of squares of character counts in a given string after removing k characters
Last Updated :
30 Apr, 2023
Given a string of lowercase alphabets and a number k, the task is to print the minimum value of the string after removal of ‘k’ characters. The value of a string is defined as the sum of squares of the count of each distinct character.
For example consider the string “saideep”, here frequencies of characters are s-1, a-1, i-1, e-2, d-1, p-1 and value of the string is 1^2 + 1^2 + 1^2 + 1^2 + 1^2 + 2^2 = 9.
Expected Time Complexity: O(k*logn)
Examples:
Input : str = abccc, K = 1
Output : 6
Explanation: We remove c to get the value as 12 + 12 + 22
Input : str = aaab, K = 2
Output : 2
Asked In: Amazon
One clear observation is that we need to remove character with highest frequency. One trick is the character ma
A Simple solution is to use sorting technique through all current highest frequency reduce up to k times. For After every reduce again sort frequency array.
A Better Solution used to Priority Queue which has to the highest element on top.
- Initialize empty priority queue.
- Count frequency of each character and Store into temp array.
- Remove K characters which have highest frequency from queue.
- Finally Count Sum of square of each element and return it.
Below is the implementation of the above idea.
C++
#include <bits/stdc++.h>
using namespace std;
const int MAX_CHAR = 26;
int minStringValue(string str, int k)
{
int l = str.length();
if (k >= l)
return 0;
int frequency[MAX_CHAR] = { 0 };
for ( int i = 0; i < l; i++)
frequency[str[i] - 'a' ]++;
priority_queue< int > q;
for ( int i = 0; i < MAX_CHAR; i++)
q.push(frequency[i]);
while (k--) {
int temp = q.top();
q.pop();
temp = temp - 1;
q.push(temp);
}
int result = 0;
while (!q.empty()) {
int temp = q.top();
result += temp * temp;
q.pop();
}
return result;
}
int main()
{
string str = "abbccc" ;
int k = 2;
cout << minStringValue(str, k) << endl;
str = "aaab" ;
k = 2;
cout << minStringValue(str, k);
return 0;
}
|
Java
import java.util.Comparator;
import java.util.PriorityQueue;
import java.util.Collections;
public class GFG {
static final int MAX_CHAR = 26 ;
static int minStringValue(String str, int k)
{
int l = str.length();
if (k >= l)
return 0 ;
int [] frequency = new int [MAX_CHAR];
for ( int i = 0 ; i < l; i++)
frequency[str.charAt(i) - 'a' ]++;
PriorityQueue<Integer> q = new PriorityQueue<>(Collections.reverseOrder());
for ( int i = 0 ; i < MAX_CHAR; i++) {
if (frequency[i] != 0 )
q.add(frequency[i]);
}
while (k != 0 ) {
q.add(q.poll() - 1 );
k--;
}
int result = 0 ;
while (!q.isEmpty()) {
result += q.peek() * q.poll();
}
return result;
}
public static void main(String args[])
{
String str = "abbccc" ;
int k = 2 ;
System.out.println(minStringValue(str, k));
str = "aaab" ;
k = 2 ;
System.out.println(minStringValue(str, k));
}
}
|
Python 3
from queue import PriorityQueue
MAX_CHAR = 26
def minStringValue( str , k):
l = len ( str )
if (k > = l):
return 0
frequency = [ 0 ] * MAX_CHAR
for i in range ( 0 , l):
frequency[ ord ( str [i]) - 97 ] + = 1
q = PriorityQueue()
for i in range ( 0 , MAX_CHAR):
q.put( - frequency[i])
while (k > 0 ):
temp = q.get()
temp = temp + 1
q.put(temp, temp)
k = k - 1
result = 0 ;
while not q.empty():
temp = q.get()
temp = temp * ( - 1 )
result + = temp * temp
return result
if __name__ = = "__main__" :
str = "abbccc"
k = 2
print (minStringValue( str , k))
str = "aaab"
k = 2
print (minStringValue( str , k))
|
C#
using System;
using System.Collections.Generic;
class GFG {
static readonly int MAX_CHAR = 26;
static int minStringValue(String str, int k)
{
int l = str.Length;
if (k >= l)
return 0;
int [] frequency = new int [MAX_CHAR];
for ( int i = 0; i < l; i++)
frequency[str[i] - 'a' ]++;
List< int > q = new List< int >();
for ( int i = 0; i < MAX_CHAR; i++)
{
if (frequency[i] != 0)
q.Add(frequency[i]);
}
while (k != 0)
{
q.Sort();
q.Reverse();
q.Add(q[0] - 1);
q.RemoveAt(0);
k--;
}
int result = 0;
while (q.Count != 0)
{
result += q[0] * q[0];
q.RemoveAt(0);
}
return result;
}
public static void Main(String []args)
{
String str = "abbccc" ;
int k = 2;
Console.WriteLine(minStringValue(str, k));
str = "aaab" ;
k = 2;
Console.WriteLine(minStringValue(str, k));
}
}
|
Javascript
<script>
let MAX_CHAR = 26;
function minStringValue(str,k)
{
let l = str.length;
if (k >= l)
return 0;
let frequency = new Array(MAX_CHAR);
for (let i=0;i<MAX_CHAR;i++)
frequency[i]=0;
for (let i = 0; i < l; i++)
frequency[str[i].charCodeAt(0) - 'a' .charCodeAt(0)]++;
let q = [];
for (let i = 0; i < MAX_CHAR; i++) {
if (frequency[i] != 0)
q.push(frequency[i]);
}
q.sort( function (a,b){ return b-a;});
while (k != 0) {
q.push(q.shift() - 1);
q.sort( function (a,b){ return b-a;});
k--;
}
let result = 0;
while (q.length!=0) {
result += q[0] * q.shift();
}
return result;
}
let str = "abbccc" ;
let k = 2;
document.write(minStringValue(str, k)+ "<br>" );
str = "aaab" ;
k = 2;
document.write(minStringValue(str, k)+ "<br>" );
</script>
|
Time Complexity: O(k*logn)
Auxiliary Space: O(N) because constant size array but priority_queue is storing characters almost the length of the string in worst case.
Efficient Approach :
We can solve it in O(N) time complexity as we need to be greedy and always remove the characters of alphabets which are higher in frequency.
Example: Let str=”abbccc” and k=2 now, alphabetCount[1]=1;//for ‘a’ alphabetCount[2]=2;//for ‘b’ alphabetCount[3]=3;//for ‘c’ maximum=3 m[1]=1(only a occur 1 times) m[2]=1(only b occur 2 times) m[3]=1(only c occur 3 times) //k=2 maximum=3 so k=k-m[maximum]//k=k-1; so now one c got removes so frequencies are a=1,b=2,c=2; so as c’s frequency got decreased by one m[maximum] will be zero and m[maximum-1] will be increased by m[maximum] so update m[2]+=m[3], m[3]=0; also maximum gets decreased by one as it is guaranteed to exist frequency one less than maximum from above. m[1]=1 , m[2]=2 , m[3]=0 and k=1; now m[maximum](i.e m[2]=2>k) so we should partially remove remove one character of either b or c so m[1]=2 0,m[2]=1 ,m[3]=0 and k=0; so, (1*1)*2 + (2*2)*1 + (3*3)*0 = 6//ans
Implementation:
C++
#include <bits/stdc++.h>
using namespace std;
const int MAX_CHAR = 26;
int minStringValue(string str, int k)
{
int alphabetCount[MAX_CHAR]= {0};
int m[str.length()] = { 0 };
for ( int i = 0; i < str.length(); i++) {
alphabetCount[str[i] - 'a' ]++;
}
int maximum = 0;
for ( int i = 0; i < MAX_CHAR; i++) {
m[alphabetCount[i]]++;
maximum = max(maximum, alphabetCount[i]);
}
while (k > 0) {
int z = m[maximum];
if (z <= k) {
k = k - z;
m[maximum] = 0;
m[maximum - 1] += z;
maximum--;
}
else {
m[maximum] -= k;
maximum--;
m[maximum] += k;
k = 0;
}
}
int ans = 0;
for ( int i = 0; i < str.length(); i++) {
ans += (i * i) * m[i];
}
return ans;
}
int main()
{
string str = "abbccc" ;
int k = 2;
cout << minStringValue(str, k) << endl;
str = "aaab" ;
k = 2;
cout << minStringValue(str, k);
return 0;
}
|
Java
import java.util.Collections;
import java.util.Comparator;
import java.util.PriorityQueue;
public class GFG {
static final int MAX_CHAR = 26 ;
static int minStringValue(String str, int k)
{
int [] alphabetCount = new int [MAX_CHAR];
int [] m = new int [str.length()];
for ( int i = 0 ; i < str.length(); i++) {
alphabetCount[str.charAt(i) - 'a' ]++;
}
int maximum = 0 ;
for ( int i = 0 ; i < MAX_CHAR; i++) {
m[alphabetCount[i]]++;
maximum = Math.max(maximum, alphabetCount[i]);
}
while (k > 0 ) {
int z = m[maximum];
if (z <= k) {
k = k - z;
m[maximum] = 0 ;
m[maximum - 1 ] += z;
maximum--;
}
else {
m[maximum] -= k;
maximum--;
m[maximum] += k;
k = 0 ;
}
}
int ans = 0 ;
for ( int i = 0 ; i < str.length(); i++) {
ans += (i * i) * m[i];
}
return ans;
}
public static void main(String args[])
{
String str = "abbccc" ;
int k = 2 ;
System.out.println(minStringValue(str, k));
str = "aaab" ;
k = 2 ;
System.out.println(minStringValue(str, k));
}
}
|
Python3
MAX_CHAR = 26
def minStringValue( str , k):
alphabetCount = []
for i in range (MAX_CHAR):
alphabetCount.append( 0 )
m = []
for i in range ( len ( str )):
m.append( 0 )
for i in range ( len ( str )):
alphabetCount[ ord ( str [i]) - ord ( 'a' )] + = 1
maximum = 0
for i in range (MAX_CHAR):
m[alphabetCount[i]] + = 1
maximum = max (maximum, alphabetCount[i])
while (k > 0 ):
z = m[maximum]
if z < = k:
k = k - z
m[maximum] = 0
m[maximum - 1 ] + = z
maximum - = 1
else :
m[maximum] - = k
maximum - = 1
m[maximum] + = k
k = 0
ans = 0
for i in range ( len ( str )):
ans = ans + (i * i) * m[i]
return ans
str = "abbccc"
k = 2
print (minStringValue( str , k))
str = "aaab"
k = 2
print (minStringValue( str , k))
|
C#
using System;
public static class GFG {
static int MAX_CHAR = 26;
static int minStringValue( string str, int k)
{
int [] alphabetCount = new int [MAX_CHAR];
int [] m = new int [str.Length];
for ( int i = 0; i < str.Length; i++) {
alphabetCount[str[i] - 'a' ]++;
}
int maximum = 0;
for ( int i = 0; i < MAX_CHAR; i++) {
m[alphabetCount[i]]++;
maximum = Math.Max(maximum, alphabetCount[i]);
}
while (k > 0) {
int z = m[maximum];
if (z <= k) {
k = k - z;
m[maximum] = 0;
m[maximum - 1] += z;
maximum--;
}
else {
m[maximum] -= k;
maximum--;
m[maximum] += k;
k = 0;
}
}
int ans = 0;
for ( int i = 0; i < str.Length; i++) {
ans += (i * i) * m[i];
}
return ans;
}
public static void Main()
{
string str = "abbccc" ;
int k = 2;
Console.Write(minStringValue(str, k));
Console.Write( "\n" );
str = "aaab" ;
k = 2;
Console.Write(minStringValue(str, k));
}
}
|
Javascript
<script>
let MAX_CHAR = 26;
function minStringValue(str,k)
{
var alphabetCount = new Array(MAX_CHAR).fill(0);
var m = new Array(str.length).fill(0);
var i;
for (i = 0; i < str.length; i++) {
alphabetCount[str.charCodeAt(i) - 97]++;
}
var maximum = 0;
for (i = 0; i < MAX_CHAR; i++) {
m[alphabetCount[i]]++;
maximum = Math.max(maximum, alphabetCount[i]);
}
while (k > 0) {
var z = m[maximum];
if (z <= k) {
k = k - z;
m[maximum] = 0;
m[maximum - 1] += z;
maximum--;
}
else {
m[maximum] -= k;
maximum--;
m[maximum] += k;
k = 0;
}
}
var ans = 0;
for (i = 0; i < str.length; i++) {
ans += (i * i) * m[i];
}
return ans;
}
let str = "abbccc" ;
let k = 2;
document.write(minStringValue(str, k)+ "<br>" );
str = "aaab" ;
k = 2;
document.write(minStringValue(str, k)+ "<br>" );
</script>
|
Time Complexity: O(N)
Space Complexity: O(N)
Similar Reads
Minimum removals required such that given string consists only of a pair of alternating characters
Given a string S, the task is to find the minimum removal of characters required such that the string S consists only of two alternating characters. Examples: Input: S = "adebbeeaebd"Output: 7Explanation: Removing all occurrences of 'b' and 'e' modifies the string to "adad", which consist of alterna
10 min read
Maximum non-repeating characters after removing K characters
Given a string S containing lowercase English alphabets of length N and an integer K such that K ? N. The task is to find the maximum number of non-repeating characters after removing K characters from the string. Examples: Input: S = "geeksforgeeks", K = 3Output: 6Explanation:Remove 1 occurrences o
8 min read
Minimum characters to be replaced in given String to make all characters same
Given a string str of size N consisting of lowercase English characters, the task is to find the minimum characters to be replaced to make all characters of string str same. Any character can be replaced by any other character. Example: Input: str="geeksforgeeks"Output: 9Explanation: Replace all the
7 min read
Count substrings having frequency of a character exceeding that of another character in a string
Given a string S of size N consisting of characters a, b, and c only, the task is to find the number of substrings of the given string S such that the frequency of character a is greater than the frequency of character c. Examples: Input: S = "abcc"Output: 2Explanation:Below are all the possible sub
15 min read
Count of ungrouped characters after dividing a string into K groups of distinct characters
Given a lower alphabetic string "S" of size N, and an integer K; the task is to find the count of characters that will remain ungrouped, after dividing the given string into K groups of distinct characters.Examples: Input: S = "stayinghomesaveslife", K = 1 Output: 6 Explanation: In the string S the
6 min read
Minimum count of distinct Strings by Rotating and Changing characters
Given a string S of length N and an integer K. The task is to find the minimum count of distinct strings by changing at most K characters of the string (into any other lowercase letters) and by rotating the string left any number of times. Examples: Input : N = 4, S = "abac", K = 1Output: 2Explanati
10 min read
Minimum cost to remove the spaces between characters of a String by rearranging the characters
Given a string str that consists of characters and spaces, the task is to find the minimum cost to reduce the number of spaces between characters of the string. Cost of moving a character for index i to index j is defined as: | i - j | Examples: Input: str = " @ $" Output: 4 Explanation: As the char
7 min read
Smallest character in a string having minimum sum of distances between consecutive repetitions
Given a string S of size N consisting of lowercase alphabets only, the task is to find the smallest character having a minimum sum of distances between its consecutive repetition. If string S consists of distinct characters only, then print "-1". Examples: Input: str = "aabbaadc"Output: b;Explanatio
7 min read
Sum of indices of Characters removed to obtain an Empty String based on given conditions
Given a string str, consisting of lowercase English alphabets, the task is to calculate the sum of indices(1-based indexing) of the characters removed to obtain an empty string by the following operations: Remove the smallest alphabet in the string.For multiple occurrences of the smallest alphabet,
13 min read
Check if string remains palindrome after removing given number of characters
Given a palindromic string str and an integer N. The task is to find if it is possible to remove exactly N characters from the given string such that the string remains a palindrome. Examples: Input: str = "abba", N = 1 Output: Yes Remove 'b' and the remaining string "aba" is still a palindrome. Inp
3 min read