Input: text = forxxorfxdofr, word =forOutput :3Explanation : Anagrams of the word for-for, orf, ofr appear in the text and hence the count is3.
Example 2
1
2
3
4
Input : text = aabaabaa, word = aaba
Output :4Explanation : Anagrams of the word aaba - aaba, abaa each appear twice in the text and hence the
count is4.
We calculate the hashmap repeatedly for the word, though we only need to compute it once.
The implementation repeatedly breaks substrings and recalculates character counts.
For example, consider:
1
Input: text = forxxorfxdofr, word =for
In the above method, we first calculate the character count for the substring “for”, then move to the next substring “orx” and recalculate the character count. This leads to redundant work for overlapping substrings like “or”. We can reduce this repetitive work using the sliding window technique.
publicclassSolution {
publicintcountOccurrenceOfAnagram(String text, String word) {
int n = text.length();
int k = word.length();
int count = 0;
// Calculate the count of each character for the given word Map<Character, Integer> wordCharCount =new HashMap<>();
for (int i = 0; i < k; i++) {
char c = word.charAt(i);
wordCharCount.put(c, wordCharCount.getOrDefault(c, 0) + 1);
}
// Store the character count for the current substring (current window) Map<Character, Integer> substrCharCount =new HashMap<>();
int windowStart = 0;
for (int windowEnd = 0; windowEnd < n; windowEnd++) {
char c = text.charAt(windowEnd);
substrCharCount.put(c, substrCharCount.getOrDefault(c, 0) + 1); // Include next char in windowif (windowEnd - windowStart + 1 == k) { // Window size reachedif (areAnagramsFreqMap(wordCharCount, substrCharCount)) {
count++;
}
// Remove the start char as we slide the windowchar startChar = text.charAt(windowStart);
if (substrCharCount.get(startChar) == 1) {
substrCharCount.remove(startChar);
} else {
substrCharCount.put(startChar, substrCharCount.get(startChar) - 1);
}
windowStart++; // Slide the window }
}
return count;
}
// Check if two character count maps are equalbooleanareAnagramsFreqMap(Map<Character, Integer> word1CharCount, Map<Character, Integer> word2CharCount) {
for (char c : word1CharCount.keySet()) {
if (!word1CharCount.get(c).equals(word2CharCount.get(c))) { // Use equals instead of != for Integer comparisonreturnfalse;
}
}
returntrue;
}
}
from collections import defaultdict
classSolution:
defcount_occurrence_of_anagram(self, text, word):
n = len(text)
k = len(word)
count =0# Calculate the count of each character for the given word word_char_count = defaultdict(int)
for c in word:
word_char_count[c] +=1# Store the character count for the current substring (current window) substr_char_count = defaultdict(int)
window_start =0for window_end in range(n):
c = text[window_end]
substr_char_count[c] +=1# Include the next char in the windowif window_end - window_start +1== k: # Window size reachedif self.are_anagrams_freq_map(word_char_count, substr_char_count):
count +=1# Remove the start char as we slide the window start_char = text[window_start]
if substr_char_count[start_char] ==1:
del substr_char_count[start_char]
else:
substr_char_count[start_char] -=1 window_start +=1# Slide the windowreturn count
defare_anagrams_freq_map(self, word1_char_count, word2_char_count):
# Check if two character count dictionaries are equalfor c in word1_char_count:
if word1_char_count[c] != word2_char_count.get(c, 0):
returnFalsereturnTrue