给定两个字符串“ S1”和“ S2”,任务是从“ S2”中不存在的“ S1”中返回最频繁的单词(使用次数最多)。如果可以使用多个单词,则按字典顺序在其中最小打印。
例子:
Input: S1 = “geeks for geeks is best place to learn”, S2 = “bad place”
Output: geeks
“geeks” is the most frequent word in S1 and is also not present in S2.
The frequency of “geeks” is 2
Input: S1 = “the quick brown fox jumps over the lazy dog”, S2 = “the brown fox jumps”
Output: dog
All the words have frequency 1.
The lexicographically smallest word is “dog”
方法:思考过程必须从创建映射以存储键值对(字符串,int)开始。随后,在更新映射和计数的同时开始从第一个字符串提取单词。对于第一个数组中存在的第二个数组中的每个单词,重置计数。最后,遍历地图,找到频率最高的单词,然后按字典顺序得到最小的单词。
算法:
- 遍历字符串S2并创建一个映射,并将其中的所有单词插入到映射中。
- 遍历字符串S1并检查在上一步创建的映射中是否不存在该单词。
- 如果单词满足条件,则直到现在为止相同单词的频率最大时,才更新答案。
- 如果单词的频率等于先前选择的单词,则根据两个字符串按字典顺序最小的单词来更新答案。
下面是上述方法的实现:
C++
// CPP implementation of above approach
#include
using namespace std;
// Function to return frequent
// word from S1 that isn't
// present in S2
string smallestFreq(string S1, string S2)
{
map banned;
// create map of banned words
for (int i = 0; i < S2.length(); ++i) {
string s = "";
while (i < S2.length() && S2[i] != ' ')
s += S2[i++];
banned[s]++;
}
map result;
string ans;
int freq = 0;
// find smallest and most frequent word
for (int i = 0; i < S1.length(); ++i) {
string s = "";
while (i < S1.length() && S1[i] != ' ')
s += S1[i++];
// check if word is not banned
if (banned[s] == 0) {
result[s]++;
if (result[s] > freq
|| (result[s] == freq && s < ans)) {
ans = s;
freq = result[s];
}
}
}
// return answer
return ans;
}
// Driver program
int main()
{
string S1 = "geeks for geeks is best place to learn";
string S2 = "bad place";
cout << smallestFreq(S1, S2);
return 0;
}
Java
// Java implementation of above approach
import java.util.HashMap;
class GFG
{
// Function to return frequent
// word from S1 that isn't
// present in S2
static String smallestFreq(String S1,
String S2)
{
HashMap banned = new HashMap<>();
// create map of banned words
for (int i = 0; i < S2.length(); i++)
{
String s = "";
while (i < S2.length() &&
S2.charAt(i) != ' ')
s += S2.charAt(i++);
banned.put(s, banned.get(s) == null ?
1 : banned.get(s) + 1);
}
HashMap result = new HashMap<>();
String ans = "";
int freq = 0;
// find smallest and most frequent word
for (int i = 0; i < S1.length(); i++)
{
String s = "";
while (i < S1.length() &&
S1.charAt(i) != ' ')
s += S1.charAt(i++);
// check if word is not banned
if (banned.get(s) == null)
{
result.put(s, result.get(s) == null ? 1 :
result.get(s) + 1);
if (result.get(s) > freq ||
(result.get(s) == freq &&
s.compareTo(ans) < 0))
{
ans = s;
freq = result.get(s);
}
}
}
// return answer
return ans;
}
// Driver Code
public static void main(String[] args)
{
String S1 = "geeks for geeks is best place to learn";
String S2 = "bad place";
System.out.println(smallestFreq(S1, S2));
}
}
// This code is contributed by
// sanjeev2552
Python3
# Python3 implementation of above approach
from collections import defaultdict
# Function to return frequent
# word from S1 that isn't
# present in S2
def smallestFreq(S1, S2):
banned = defaultdict(lambda:0)
i = 0
# create map of banned words
while i < len(S2):
s = ""
while i < len(S2) and S2[i] != ' ':
s += S2[i]
i += 1
i += 1
banned[s] += 1
result = defaultdict(lambda:0)
ans = ""
freq = 0
i = 0
# find smallest and most frequent word
while i < len(S1):
s = ""
while i < len(S1) and S1[i] != ' ':
s += S1[i]
i += 1
i += 1
# check if word is not banned
if banned[s] == 0:
result[s] += 1
if (result[s] > freq or
(result[s] == freq and s < ans)):
ans = s
freq = result[s]
# return answer
return ans
# Driver Code
if __name__ == "__main__":
S1 = "geeks for geeks is best place to learn"
S2 = "bad place"
print(smallestFreq(S1, S2))
# This code is contributed
# by Rituraj Jain
C#
// C# implementation of above approach
using System;
using System.Collections.Generic;
class GFG
{
// Function to return frequent
// word from S1 that isn't
// present in S2
static String smallestFreq(String S1,
String S2)
{
Dictionary banned = new Dictionary();
// create map of banned words
for (int i = 0; i < S2.Length; i++)
{
String s = "";
while (i < S2.Length &&
S2[i] != ' ')
s += S2[i++];
if(banned.ContainsKey(s))
{
var val = banned[s];
banned.Remove(s);
banned.Add(s, val + 1);
}
else
{
banned.Add(s, 1);
}
}
Dictionary result = new Dictionary();
String ans = "";
int freq = 0;
// find smallest and most frequent word
for (int i = 0; i < S1.Length; i++)
{
String s = "";
while (i < S1.Length &&
S1[i] != ' ')
s += S1[i++];
// check if word is not banned
if (!banned.ContainsKey(s))
{
if(result.ContainsKey(s))
{
var val = result[s];
result.Remove(s);
result.Add(s, val + 1);
}
else
{
result.Add(s, 1);
}
if (result[s] > freq ||
(result[s] == freq &&
s.CompareTo(ans) < 0))
{
ans = s;
freq = result[s];
}
}
}
// return answer
return ans;
}
// Driver Code
public static void Main(String[] args)
{
String S1 = "geeks for geeks is best place to learn";
String S2 = "bad place";
Console.WriteLine(smallestFreq(S1, S2));
}
}
// This code is contributed by PrinciRaj1992
输出:
geeks
复杂度分析:
- 时间复杂度: O(n),其中n是字符串的长度。
需要对字符串一次遍历。 - 空间复杂度: O(n)。
一个字符串中最多可以有n个单词。该映射需要O(n)空间来存储字符串。