題目鏈接: https://leetcode.com/problems/longest-substring-without-repeating-characters/description/
Description
Given a string, find the length of the longest substring without repeating characters.
Examples:
Given "abcabcbb"
, the answer is "abc"
, which the length is 3.
Given "bbbbb"
, the answer is "b"
, with the length of 1.
Given "pwwkew"
, the answer is "wke"
, with the length of 3. Note that the answer must be a substring, "pwke"
is a subsequence and not a substring.
解題思路
題意爲找到最長的無重複字符的子串的長度。
因爲共有 256 種不同的字符,所以可以用一個數組來記錄每一個字符最後一次出現的下標。用變量 start
來記錄當前子串第一個字符的下標,遍歷字符串,若發現字符 s[i]
對應的最後一次出現的下標大於等於 start
,即表示 s[i]
在該子串中已經出現過,則當前子串的下標區間爲 [start, i - 1]
,更新長度記錄。並且,新的子串起始位置應該爲 s[i]
上次出現的下標後一個位置,這樣才能保證最長這一個條件。
另外,由於更新長度記錄是在遍歷中進行的,因此若最長子串包含最後一個字符,在遍歷過程中就不能更新該長度記錄,所以要在遍歷外邊再加一個長度記錄更新。
舉個例子,s = "abac"
,記錄字符最後一次出現下標的數組爲 alpha[256]
,'a'
的 ascii 碼爲 97。
i == 0, s[i] == 'a'
:start = 0, alpha[97] = 0
,子串爲"a"
。i == 1, s[i] == 'b'
:alpha[98] = 1
,子串爲"ab"
。i == 2, s[i] == 'a'
:alpha[97] == 0 >= start
=> 當前子串"ab"
已經有'a'
存在,更新長度記錄爲2
,並且應該從'b'
開始下一個子串,所以start = alpha[97] + 1
,即爲1
。alpha[97] = 2
,子串爲"ba"
。i == 3, s[i] == 'c'
:alpha[99] = 3
,子串爲"bac"
,更新長度記錄爲3
。
Code
class Solution {
public:
int lengthOfLongestSubstring(string s) {
vector<int> alpha(256, -1);
int res = 0, start = 0;
for (int i = 0; i < s.size(); ++i) {
if (alpha[s[i]] >= start) {
res = max(i - start, res);
start = alpha[s[i]] + 1;
}
alpha[s[i]] = i;
}
res = max((int)(s.size() - start), res);
return res;
}
};