Longest Substring Without Repeating Characters medium
Problem Statement
Given a string s
, find the length of the longest substring without repeating characters.
Example 1:
Input: s = "abcabcbb" Output: 3 Explanation: The answer is "abc", with the length of 3.
Example 2:
Input: s = "bbbbb" Output: 1 Explanation: The answer is "b", with the length of 1.
Steps
-
Initialization: We'll use a
Map
to store the last seen index of each character in the string. We'll also initialize two pointers,start
andend
, both to 0.start
represents the beginning of the current substring without repeating characters, andend
represents the end. We'll also initializemaxLength
to 0 to store the length of the longest substring found so far. -
Iteration: We iterate through the string using the
end
pointer. -
Character Check: For each character at
s[end]
:- If the character is not in the
Map
(or its last seen index is less thanstart
), it means we haven't seen this character in the current substring. We add it to theMap
with its index (end
), and updatemaxLength
if necessary. We then move theend
pointer to the next character. - If the character is in the
Map
and its last seen index is greater than or equal tostart
, it means we've encountered a repeating character within the current substring. We move thestart
pointer to the right of the previous occurrence of this character (last seen index + 1), effectively shrinking the current substring to remove the repeating character. We then update the character's last seen index in theMap
to the currentend
index.
- If the character is not in the
-
Return: After iterating through the entire string,
maxLength
will hold the length of the longest substring without repeating characters.
Explanation
The algorithm uses a sliding window approach. The window expands as long as we encounter unique characters. When we encounter a repeating character, we shrink the window from the left (moving start
) until the repeating character is removed from the current substring. The Map
efficiently tracks the last seen index of each character, allowing for quick lookups during the character check.
Code
function lengthOfLongestSubstring(s: string): number {
const charMap = new Map<string, number>();
let start = 0;
let end = 0;
let maxLength = 0;
while (end < s.length) {
const char = s[end];
if (!charMap.has(char) || charMap.get(char)! < start) {
charMap.set(char, end);
maxLength = Math.max(maxLength, end - start + 1);
end++;
} else {
start = charMap.get(char)! + 1;
charMap.set(char, end);
end++;
}
}
return maxLength;
};
Complexity
-
Time Complexity: O(n), where n is the length of the string. We iterate through the string at most twice (once with
end
and potentially multiple times withstart
, but the total number of operations is still linear). -
Space Complexity: O(min(m, n)), where n is the length of the string and m is the size of the character set (256 for ASCII characters). The space used by the
Map
depends on the number of unique characters in the string, which is at most the length of the string or the size of the character set, whichever is smaller. In the worst case (all characters unique), it will be O(n).