给定一个字符串S和整数K,任务是,以检查是否有可能这些字符分配到两个字符串,使得具有在两个字符串的频率k的字符计数等于。
如果可能,则打印一个由1和2组成的序列,表示哪个字符应该放在哪个字符串。否则,打印NO 。
注意:这些新字符串可以为空。
例子:
Input: S = “abbbccc”, K = 1
Output: 1111211
Explanation:
The two strings are “abbbcc” and “c”.
Hence, both the strings have exactly 1 character having frequency K( = 1).
Input: S = “aaaa”, K = 3
Output: 1111
Explanation:
Strings can be split into “aaaa” and “”.
Hence, no character has frequency 3 in both the strings.
方法:
请按照以下步骤解决问题:
- 检查以下三个条件以确定是否可以拆分:
1. 如果初始字符串频率为K的字符总数为偶数,则可以将这些字符等量放入两个字符串,其余字符(频率不等于K )可以放入任意一个两组。
2.如果初始字符串频率为K的字符总数为奇数,则如果初始字符串中存在频率大于K但不等于2K的字符,则可能存在这样的分布。
Illustration:
S =”abceeee”, K = 1
Split into “abeee” and “ce”. Hence, both the strings have 2 characters with frequency 1.
3.如果初始字符串频率为K的字符总数为奇数,则如果初始字符串中存在频率为2K的字符,则可能存在这样的分布。
Illustration:
S =”aaaabbccdde”, K = 2
Split into “aabbc” and “aaddce” so that both the strings have two characters with frequency 2.
- 如果上面提到的三个条件都失败了,那么答案是“NO” 。
下面是上述方法的实现:
C++
// C++ implementation of the
// above approach
#include
using namespace std;
// Function to print the
// arrangement of characters
void DivideString(string s, int n,
int k)
{
int i, c = 0, no = 1;
int c1 = 0, c2 = 0;
// Stores frequency of
// characters
int fr[26] = { 0 };
string ans = "";
for (i = 0; i < n; i++) {
fr[s[i] - 'a']++;
}
char ch, ch1;
for (i = 0; i < 26; i++) {
// Count the character
// having frequency K
if (fr[i] == k) {
c++;
}
// Count the character
// having frequency
// greater than K and
// not equal to 2K
if (fr[i] > k
&& fr[i] != 2 * k) {
c1++;
ch = i + 'a';
}
if (fr[i] == 2 * k) {
c2++;
ch1 = i + 'a';
}
}
for (i = 0; i < n; i++)
ans = ans + "1";
map mp;
if (c % 2 == 0 || c1 > 0 || c2 > 0) {
for (i = 0; i < n; i++) {
// Case 1
if (fr[s[i] - 'a'] == k) {
if (mp.find(s[i])
!= mp.end()) {
ans[i] = '2';
}
else {
if (no <= (c / 2)) {
ans[i] = '2';
no++;
mp[s[i]] = 1;
}
}
}
}
// Case 2
if (c % 2 == 1 && c1 > 0) {
no = 1;
for (i = 0; i < n; i++) {
if (s[i] == ch && no <= k) {
ans[i] = '2';
no++;
}
}
}
// Case 3
if (c % 2 == 1 && c1 == 0) {
no = 1;
int flag = 0;
for (int i = 0; i < n; i++) {
if (s[i] == ch1 && no <= k) {
ans[i] = '2';
no++;
}
if (fr[s[i] - 'a'] == k
&& flag == 0
&& ans[i] == '1') {
ans[i] = '2';
flag = 1;
}
}
}
cout << ans << endl;
}
else {
// If all cases fail
cout << "NO" << endl;
}
}
// Driver Code
int main()
{
string S = "abbbccc";
int N = S.size();
int K = 1;
DivideString(S, N, K);
return 0;
}
Java
// Java program for the above problem
import java.util.*;
class GFG{
// Function to print the
// arrangement of characters
public static void DivideString(String s, int n,
int k)
{
int i, c = 0, no = 1;
int c1 = 0, c2 = 0;
// Stores frequency of
// characters
int[] fr = new int[26];
char[] ans = new char[n];
for(i = 0; i < n; i++)
{
fr[s.charAt(i) - 'a']++;
}
char ch = 'a', ch1 = 'a';
for(i = 0; i < 26; i++)
{
// Count the character
// having frequency K
if (fr[i] == k)
{
c++;
}
// Count the character
// having frequency
// greater than K and
// not equal to 2K
if (fr[i] > k && fr[i] != 2 * k)
{
c1++;
ch = (char)(i + 'a');
}
if (fr[i] == 2 * k)
{
c2++;
ch1 = (char)(i + 'a');
}
}
for(i = 0; i < n; i++)
ans[i] = '1';
HashMap mp = new HashMap<>();
if (c % 2 == 0 || c1 > 0 || c2 > 0)
{
for(i = 0; i < n; i++)
{
// Case 1
if (fr[s.charAt(i) - 'a'] == k)
{
if (mp.containsKey(s.charAt(i)))
{
ans[i] = '2';
}
else
{
if (no <= (c / 2))
{
ans[i] = '2';
no++;
mp.replace(s.charAt(i), 1);
}
}
}
}
// Case 2
if ( (c % 2 == 1) && (c1 > 0) )
{
no = 1;
for(i = 0; i < n; i++)
{
if (s.charAt(i) == ch && no <= k)
{
ans[i] = '2';
no++;
}
}
}
// Case 3
if (c % 2 == 1 && c1 == 0)
{
no = 1;
int flag = 0;
for(i = 0; i < n; i++)
{
if (s.charAt(i) == ch1 && no <= k)
{
ans[i] = '2';
no++;
}
if (fr[s.charAt(i) - 'a'] == k &&
flag == 0 && ans[i] == '1')
{
ans[i] = '2';
flag = 1;
}
}
}
System.out.println(ans);
}
else
{
// If all cases fail
System.out.println("NO");
}
}
// Driver code
public static void main(String[] args)
{
String S = "abbbccc";
int N = S.length();
int K = 1;
DivideString(S, N, K);
}
}
// This code is contributed by divyeshrabadiya07
Python3
# Python3 implementation of the
# above approach
# Function to print the
# arrangement of characters
def DivideString(s, n, k):
c = 0
no = 1
c1 = 0
c2 = 0
# Stores frequency of
# characters
fr = [0] * 26
ans = []
for i in range(n):
fr[ord(s[i]) - ord('a')] += 1
for i in range(26):
# Count the character
# having frequency K
if (fr[i] == k):
c += 1
# Count the character having
# frequency greater than K and
# not equal to 2K
if (fr[i] > k and fr[i] != 2 * k):
c1 += 1
ch = chr(ord('a') + i)
if (fr[i] == 2 * k):
c2 += 1
ch1 = chr(ord('a') + i)
for i in range(n):
ans.append("1")
mp = {}
if (c % 2 == 0 or c1 > 0 or c2 > 0):
for i in range(n):
# Case 1
if (fr[ord(s[i]) - ord('a')] == k):
if (s[i] in mp):
ans[i] = '2'
else:
if (no <= (c // 2)):
ans[i] = '2'
no += 1
mp[s[i]] = 1
# Case 2
if (c % 2 == 1 and c1 > 0):
no = 1
for i in range(n):
if (s[i] == ch and no <= k):
ans[i] = '2'
no += 1
# Case 3
if (c % 2 == 1 and c1 == 0):
no = 1
flag = 0
for i in range(n):
if (s[i] == ch1 and no <= k):
ans[i] = '2'
no += 1
if (fr[s[i] - 'a'] == k and
flag == 0 and
ans[i] == '1'):
ans[i] = '2'
flag = 1
print("".join(ans))
else:
# If all cases fail
print("NO")
# Driver Code
if __name__ == '__main__':
S = "abbbccc"
N = len(S)
K = 1
DivideString(S, N, K)
# This code is contributed by mohit kumar 29
C#
// C# program for the above problem
using System;
using System.Collections.Generic;
class GFG{
// Function to print the
// arrangement of characters
public static void DivideString(string s, int n,
int k)
{
int i, c = 0, no = 1;
int c1 = 0, c2 = 0;
// Stores frequency of
// characters
int[] fr = new int[26];
char[] ans = new char[n];
for(i = 0; i < n; i++)
{
fr[s[i] - 'a']++;
}
char ch = 'a', ch1 = 'a';
for(i = 0; i < 26; i++)
{
// Count the character
// having frequency K
if (fr[i] == k)
{
c++;
}
// Count the character having
// frequency greater than K and
// not equal to 2K
if (fr[i] > k && fr[i] != 2 * k)
{
c1++;
ch = (char)(i + 'a');
}
if (fr[i] == 2 * k)
{
c2++;
ch1 = (char)(i + 'a');
}
}
for(i = 0; i < n; i++)
ans[i] = '1';
Dictionary mp = new Dictionary();
if (c % 2 == 0 || c1 > 0 || c2 > 0)
{
for(i = 0; i < n; i++)
{
// Case 1
if (fr[s[i] - 'a'] == k)
{
if (mp.ContainsKey(s[i]))
{
ans[i] = '2';
}
else
{
if (no <= (c / 2))
{
ans[i] = '2';
no++;
mp[s[i]] = 1;
}
}
}
}
// Case 2
if ( (c % 2 == 1) && (c1 > 0) )
{
no = 1;
for(i = 0; i < n; i++)
{
if (s[i]== ch && no <= k)
{
ans[i] = '2';
no++;
}
}
}
// Case 3
if (c % 2 == 1 && c1 == 0)
{
no = 1;
int flag = 0;
for(i = 0; i < n; i++)
{
if (s[i] == ch1 && no <= k)
{
ans[i] = '2';
no++;
}
if (fr[s[i] - 'a'] == k &&
flag == 0 && ans[i] == '1')
{
ans[i] = '2';
flag = 1;
}
}
}
Console.Write(ans);
}
else
{
// If all cases fail
Console.Write("NO");
}
}
// Driver code
public static void Main(string[] args)
{
string S = "abbbccc";
int N = S.Length;
int K = 1;
DivideString(S, N, K);
}
}
// This code is contributed by rutvik_56
Javascript
1111211
时间复杂度: O(N)
辅助空间: O(N)
如果您希望与专家一起参加现场课程,请参阅DSA 现场工作专业课程和学生竞争性编程现场课程。