3456. Find Special Substring of Length K
Problem Description
You are given a string s
and an integer k
.
Determine if there exists a substring of length exactly k
in s
that satisfies the following conditions:
- The substring consists of only one distinct character (e.g., "aaa" or "bbb").
- If there is a character immediately before the substring, it must be different from the character in the substring.
- If there is a character immediately after the substring, it must also be different from the character in the substring.
Return true
if such a substring exists. Otherwise, return false
.
Intuition
The problem requires finding consecutive identical characters in the string that form a segment of exact length k
, ensuring that the characters before and after this segment differ from it, if they exist.
The solution approach uses the two-pointer technique:
- Initialize two pointers,
l
andr
, both starting at the beginning of the strings
. - Expand the right pointer
r
as long as the character at this pointer matches the character atl
. This identifies a segment of consecutive identical characters. - Once a different character is found or the end of the string is reached, check if the length of this segment (
r - l
) is exactlyk
. - If such a segment is found, return
true
. Otherwise, resetl
tor
and continue searching through the string. - If no suitable segment is found by the end of the string, return
false
.
This approach effectively traverses the string, examining each segment of consecutive identical characters efficiently.
Solution Approach
To solve this problem, the Two Pointers technique is adopted, aiming to efficiently identify segments of consecutive identical characters in the string s
of exact length k
. Here is the detailed approach:
-
Initialize a pointer
l
at the start of the string and calculate the lengthn
of the strings
. -
Use a loop to increment the pointer
l
until reaching the end of the string:-
Within this loop, initialize another pointer
r
starting froml
. Mover
to the right as long ass[r]
is equal tos[l]
. This process identifies a block of consecutive identical characters. -
Once a character different from
s[l]
is encountered or the end of the string is reached, check the length of this block: ifr - l
equalsk
, it means a valid substring is found, and the function should returnTrue
.
-
-
If the loop completes without finding any valid substring, return
False
.
The approach efficiently checks each character only once and correctly identifies segments of exact length k
, making it optimal for the given problem constraints. The algorithm can be represented as follows:
class Solution:
def hasSpecialSubstring(self, s: str, k: int) -> bool:
l, n = 0, len(s)
while l < n:
r = l
while r < n and s[r] == s[l]:
r += 1
if r - l == k:
return True
l = r
return False
This solution leverages the simple yet powerful two-pointer technique, which ensures traversal of the string is efficient, achieving the goal with minimal iterations.
Ready to land your dream job?
Unlock your dream job with a 2-minute evaluator for a personalized learning plan!
Start EvaluatorExample Walkthrough
Let's walk through the solution with an example. Consider the string s = "aabbba"
and k = 3
.
-
Initialization:
- Start with pointers
l
andr
at the beginning of the string (l = 0
,r = 0
). - The length of the string
n
is 6.
- Start with pointers
-
First iteration:
l = 0
: Character ats[l]
is'a'
.- Move
r
to the right as long ass[r]
is equal tos[l]
. - The substring from
s[0]
tos[1]
is "aa". Sincer
becomes 2 and (r - l
equals 2), it's not equal tok
. So, resetl
tor
(now bothl
andr
are 2).
-
Second iteration:
l = 2
: Character ats[l]
is'b'
.- Move
r
to the right as long ass[r]
equalss[l]
. - The substring from
s[2]
tos[4]
is "bbb". Here,r
becomes 5 and (r - l
equals 3). This matchesk
, and the character immediately before the substrings[1]
is'a'
, which is different from'b'
. Hence, the conditions are satisfied. - Return
True
.
With this example, the solution evaluates each block of consecutive characters and checks if the conditions are satisfied efficiently using the two-pointer approach.
Solution Implementation
1class Solution:
2 def hasSpecialSubstring(self, s: str, k: int) -> bool:
3 # Initialize two pointers:
4 # l is the start of the current substring, and r is used to find the end of the same-character substring
5 l, n = 0, len(s)
6
7 # Iterate over the string until the end
8 while l < n:
9 r = l # Start the r pointer at the current position of l
10
11 # Expand r until a different character is found
12 while r < n and s[r] == s[l]:
13 r += 1
14
15 # Check the length of the substring of similar consecutive characters
16 if r - l == k:
17 return True # Return True if the desired length k is found
18
19 # Move the l pointer to the position of r, to start a new check
20 l = r
21
22 # Return False if no such substring exists
23 return False
24
1class Solution {
2 public boolean hasSpecialSubstring(String s, int k) {
3 int n = s.length(); // Get the length of the input string.
4
5 // Traverse the string with two pointers: l (left) and r (right).
6 for (int l = 0; l < n;) {
7 int r = l + 1;
8
9 // Expand the right pointer while the characters at l and r are the same.
10 while (r < n && s.charAt(r) == s.charAt(l)) {
11 r++;
12 }
13
14 // Check if the length of the substring of identical characters is equal to k.
15 if (r - l == k) {
16 return true; // Found a substring of exactly k identical characters.
17 }
18
19 // Move the left pointer to the next new character.
20 l = r;
21 }
22
23 // If no such substring is found, return false.
24 return false;
25 }
26}
27
1class Solution {
2public:
3 // Function to determine if there is a special substring of length `k` in string `s`
4 bool hasSpecialSubstring(string s, int k) {
5 int n = s.length(); // Length of the string `s`
6
7 // Loop through the string with `l` as the start of a potential special substring
8 for (int l = 0; l < n;) {
9 int r = l + 1; // Start with `r` as next character after `l`
10
11 // Move `r` to the right as long as characters at position `r` and `l` are the same
12 while (r < n && s[r] == s[l]) {
13 ++r;
14 }
15
16 // Check if the length of the substring from `l` to `r` is exactly `k`
17 if (r - l == k) {
18 return true; // Found a special substring, return true
19 }
20
21 // Move `l` to the position of `r` to check for the next potential substring
22 l = r;
23 }
24
25 // If no such substring found, return false
26 return false;
27 }
28};
29
1function hasSpecialSubstring(s: string, k: number): boolean {
2 const n = s.length; // Get the length of the input string
3 for (let left = 0; left < n; ) { // Start iterating from the first character
4 let right = left + 1; // Initialize the right pointer for comparison
5 // Extend the right pointer as long as the character at right is equal to the character at left
6 while (right < n && s[right] === s[left]) {
7 right++;
8 }
9 // Check if the length of the substring [left, right) is equal to k
10 if (right - left === k) {
11 return true; // Return true if a valid substring is found
12 }
13 left = right; // Move the left pointer to the position of right for the next iteration
14 }
15 return false; // Return false if no valid substring of length k is found
16}
17
Time and Space Complexity
The time complexity of the code is O(n)
, where n
is the length of the string s
. This is because the algorithm makes a single pass through the string, checking consecutive characters and counting their occurrences without revisiting any part of the string.
The space complexity of the code is O(1)
, as it utilizes a constant amount of extra space for variables l
, r
, and n
, irrespective of the size of the input string.
Learn more about how to find time and space complexity quickly.
Which of the two traversal algorithms (BFS and DFS) can be used to find whether two nodes are connected?
Recommended Readings
Coding Interview Patterns Your Personal Dijkstra's Algorithm to Landing Your Dream Job The goal of AlgoMonster is to help you get a job in the shortest amount of time possible in a data driven way We compiled datasets of tech interview problems and broke them down by patterns This way
Recursion Recursion is one of the most important concepts in computer science Simply speaking recursion is the process of a function calling itself Using a real life analogy imagine a scenario where you invite your friends to lunch https algomonster s3 us east 2 amazonaws com recursion jpg You first
Runtime Overview When learning about algorithms and data structures you'll frequently encounter the term time complexity This concept is fundamental in computer science and offers insights into how long an algorithm takes to complete given a certain input size What is Time Complexity Time complexity represents the amount of time
Want a Structured Path to Master System Design Too? Don’t Miss This!