题目描述
给定一个字符串,请你找出其中不含有重复字符的 最长子串 的长度。
示例一:
输入: "abcabcbb"
输出: 3
解释: 因为无重复字符的最长子串是 "abc",所以其长度为 3。
示例二:
输入: "bbbbb"
输出: 1
解释: 因为无重复字符的最长子串是 "b",所以其长度为 1。
示例三:
输入: "pwwkew"
输出: 3
解释: 因为无重复字符的最长子串是 "wke",所以其长度为 3。
请注意,你的答案必须是 子串 的长度,"pwke" 是一个子序列,不是子串。
首先我们看看这个题的示例3,该示例中提示我们这个题需要求的字符串的子串而不是子序列,我们具体来看看什么是子串,什么是子序列。
子串:字符串中任意个连续的字符组成的子序列称为该串的子串。注意子串强调字符的连续性
分析
假设子串里含有重复字符,则父串一定含有重复字符,单个子问题就可以决定父问题,因此可以用贪心法。跟动规不同,动规里,单个子问题只能影响父问题,不足以决定父问题。
从左往右扫描,当遇到重复字母时,以上一个重复字母的index 1,作为新的搜索起始位置,直到最后一个字母,复杂度是o(n)。
c 代码
class solution{
public:
int lengthoflongestsubstring(string s) {
const int ascii_max = 255;
int last[ascii_max]; //记录字符上次出现的位置
int start = 0; //记录当前子串的起始位置
memset(last, -1, sizeof(ascii_max));
int max_len = 0;
for (int i=0; i < s.size(); i) {
if (last[s[i]] >= start) {
max_len = std::max(i-start, max_len);
start = last[s[i]] 1;
}
last[s[i]] = i;
}
return std::max((int)s.size() - start, max_len); //别忘了最后一次,例如"abcd"
}
};