📜  除去ķ字符后,最大非重复字符

📅  最后修改于: 2021-05-05 00:46:33             🧑  作者: Mango

给定一个字符串S,其中包含长度为N的小写英语字母和一个整数K ,使得K≤N 。任务是从字符串删除K个字符后,找到不重复字符的最大数目。

例子:

幼稚的方法:幼稚的想法是删除给定字符串所有可能的K个字符,然后在所有形成的字符串找到非重复字符。打印所有非重复字符的最大值。
时间复杂度: O(N!),其中N是给定字符串的长度。
辅助空间: O(NK)

高效方法:要优化上述方法,

步骤如下:

  1. 创建一个哈希表来存储每个元素的频率。
  2. 将每个元素的频率插入向量V中,并按升序对向量V进行排序。
  3. 对于向量V的每个元素(例如currentElement ),在KcurrentElement – 1中找到最小值,然后将KV [i]减去两者中的最小值。
  4. 重复上述步骤,直到K不为零。
  5. 向量V中1s计数给出了删除K个字符后的最大非重复字符数。

下面是上述方法的实现:

C++
// C++ program for the above approach
  
#include 
using namespace std;
  
// Function to find maximum distinct
// character after removing K character
int maxDistinctChar(string s, int n, int k)
{
    // Freq implemented as hash table to
    // store frequency of each character
    unordered_map freq;
  
    // Store frequency of each character
    for (int i = 0; i < n; i++)
        freq[s[i]]++;
  
    vector v;
  
    // Insert each frequency in v
    for (auto it = freq.begin();
         it != freq.end(); it++) {
        v.push_back(it->second);
    }
  
    // Sort the freq of character in
    // non-decresing order
    sort(v.begin(), v.end());
  
    // Traverse the vector
    for (int i = 0; i < v.size(); i++) {
        int mn = min(v[i] - 1, k);
  
        // Update v[i] and k
        v[i] -= mn;
        k -= mn;
    }
  
    // If K is still not 0
    if (k > 0) {
  
        for (int i = 0; i < v.size(); i++) {
            int mn = min(v[i], k);
            v[i] -= mn;
            k -= mn;
        }
    }
  
    // Store the final answer
    int res = 0;
    for (int i = 0; i < v.size(); i++)
  
        // Count this character if freq 1
        if (v[i] == 1)
            res++;
  
    // Return count of distinct characters
    return res;
}
  
// Driver Code
int main()
{
    // Given string
    string S = "geeksforgeeks";
  
    int N = S.size();
  
    // Given k
    int K = 1;
  
    // Function Call
    cout << maxDistinctChar(S, N, K);
  
    return 0;
}


Java
// Java program for the above approach
import java.util.*;
class GFG{
  
// Function to find maximum distinct
// character after removing K character
static int maxDistinctChar(char []s, int n, int k)
{
    // Freq implemented as hash table to
    // store frequency of each character
    HashMap freq  = new HashMap();
  
    // Store frequency of each character
    for (int i = 0; i < n; i++) 
    {
        if(freq.containsKey((int)s[i]))
        {
            freq.put((int)s[i], 
                     freq.get((int)s[i]) + 1);
        }
        else
        {
            freq.put((int)s[i], 1);
        }
    }
  
    Vector v = new Vector();
  
    // Insert each frequency in v
    for (Map.Entry it : freq.entrySet()) 
    {
        v.add(it.getValue());
    }
  
    // Sort the freq of character in
    // non-decresing order
    Collections.sort(v);
  
    // Traverse the vector
    for (int i = 0; i < v.size(); i++) 
    {
        int mn = Math.min(v.get(i) - 1, k);
  
        // Update v[i] and k
        v.set(i, v.get(i) - mn);
        k -= mn;
    }
  
    // If K is still not 0
    if (k > 0) 
    {
        for (int i = 0; i < v.size(); i++) 
        {
            int mn = Math.min(v.get(i), k);
            v.set(i, v.get(i) - mn);
            k -= mn;
        }
    }
  
    // Store the final answer
    int res = 0;
    for (int i = 0; i < v.size(); i++)
  
        // Count this character if freq 1
        if (v.get(i) == 1)
            res++;
  
    // Return count of distinct characters
    return res;
}
  
// Driver Code
public static void main(String[] args)
{
    // Given String
    String S = "geeksforgeeks";
  
    int N = S.length();
  
    // Given k
    int K = 1;
  
    // Function Call
    System.out.print(maxDistinctChar(S.toCharArray(), 
                                     N, K));
}
}
  
// This code is contributed by shikhasingrajput


Python3
# Python3 program for the above approach
from collections import defaultdict
  
# Function to find maximum distinct
# character after removing K character
def maxDistinctChar(s, n, k):
  
    # Freq implemented as hash table to
    # store frequency of each character
    freq = defaultdict (int)
  
    # Store frequency of each character
    for i in range (n):
        freq[s[i]] += 1
  
    v = []
  
    # Insert each frequency in v
    for it in freq.values():
        v.append(it)
  
    # Sort the freq of character in
    # non-decresing order
    v.sort()
  
    # Traverse the vector
    for i in range (len(v)):
        mn = min(v[i] - 1, k)
  
        # Update v[i] and k
        v[i] -= mn
        k -= mn
  
    # If K is still not 0
    if (k > 0):
        for i in range (len(v)):
            mn = min(v[i], k);
            v[i] -= mn
            k -= mn
  
    # Store the final answer
    res = 0
    for i in range (len(v)):
  
        # Count this character if freq 1
        if (v[i] == 1):
            res += 1
  
    # Return count of distinct characters
    return res
  
# Driver Code
if __name__ == "__main__":
    
    # Given string
    S = "geeksforgeeks"
  
    N = len(S)
  
    # Given k
    K = 1
  
    # Function Call
    print(maxDistinctChar(S, N, K))
  
# This code is contributed by Chitranayal


C#
// C# program for the above approach
using System;
using System.Collections.Generic;
  
class GFG{
  
// Function to find maximum distinct
// character after removing K character
static int maxDistinctChar(char []s, int n, int k)
{
      
    // Freq implemented as hash table to
    // store frequency of each character
    Dictionary freq = new Dictionary();
  
    // Store frequency of each character
    for(int i = 0; i < n; i++) 
    {
        if(freq.ContainsKey((int)s[i]))
        {
            freq[(int)s[i]] = freq[(int)s[i]] + 1;
        }
        else
        {
            freq.Add((int)s[i], 1);
        }
    }
  
    List v = new List();
  
    // Insert each frequency in v
    foreach(KeyValuePair it in freq) 
    {
        v.Add(it.Value);
    }
  
    // Sort the freq of character in
    // non-decresing order
    v.Sort();
  
    // Traverse the vector
    for(int i = 0; i < v.Count; i++) 
    {
        int mn = Math.Min(v[i] - 1, k);
  
        // Update v[i] and k
        v[i] = v[i] - mn;
        k -= mn;
    }
  
    // If K is still not 0
    if (k > 0) 
    {
        for(int i = 0; i < v.Count; i++) 
        {
            int mn = Math.Min(v[i], k);
            v[i] = v[i] - mn;
            k -= mn;
        }
    }
  
    // Store the readonly answer
    int res = 0;
    for(int i = 0; i < v.Count; i++)
  
        // Count this character if freq 1
        if (v[i] == 1)
            res++;
  
    // Return count of distinct characters
    return res;
}
  
// Driver Code
public static void Main(String[] args)
{
      
    // Given String
    String S = "geeksforgeeks";
  
    int N = S.Length;
  
    // Given k
    int K = 1;
  
    // Function call
    Console.Write(maxDistinctChar(S.ToCharArray(), 
                                  N, K));
}
}
  
// This code is contributed by Amit Katiyar


输出:
4

时间复杂度: O(N)
辅助空间: O(26)