思想:利用hash的方法记录某个字符是否重复出现,空间为256个int,然后逐个探测以每个字符开始出现的最大长度,当第K个字符与前面第i个字符重复时则直接从第i+1个字符开始探测最大长度。此种解法为45ms,看到时间排名比较靠后就去看了别人的解法,发现可以进一步优化:当从第i+1个字符开始探测时可以直接从第k+1个字符开始,不必从第i+1个开始。
刚开始使用map做hash的实现,发现超时(map维护一个有序序列,每次插入需logN的时间,这是第二次在这里超时了,看到别人的解法后,发现可以使用unsorted_map),后改用int[256]的数组实现hash,但没做第二次优化(每次都需memset(array,-1,256*sizeof(int)) )用了42ms,后来实现做了第二次优化时间为21ms。
下面给出代码:
使用map超时代码:
class Solution {
public:
int lengthOfLongestSubstring(string s) {
map<char,int> mp;
typedef pair<char,int> mypair;
pair< map<char,int>::iterator,bool > pr;
int len = s.length(),count = 0,max = 0;
if( len <= 1 )
return len;
for( int i = 0; i < len ;)
{
pr = mp.insert( mypair(s[i],i) );
if( pr.second )
{
count++;
i++;
}
else
{
max = max > count ? max : count;
i = pr.first->second + 1;
count = 0;
mp.clear();
}
}
max = max > count ? max : count;
return max;
}
};
未做第二次优化45ms代码:
class Solution {
public:
int lengthOfLongestSubstring(string s) {
int arr[256];
memset(arr,-1,sizeof(int)*256);
int len = s.length(),count = 0,max = 0;
int temp,index;
if( len <= 1 )
return len;
for( int i = 0; i < len ;)
{
index = (int)s[i];
temp = arr[index];
//cout<<temp<<" "<<endl;
if( temp == -1 )
{
arr[index] = i;
count++;
i++;
}
else
{
max = max > count ? max : count;
i = temp + 1;
count = 0;
memset(arr,-1,sizeof(int)*256);
}
}
max = max > count ? max : count;
return max;
}
};
第二次优化后21ms代码:
class Solution {
public:
int lengthOfLongestSubstring(string s) {
int arr[256];
memset(arr,-1,sizeof(int)*256);
int len = s.length(),count = 0,max = 0;
int temp,index,start = 0;
if( len <= 1 )
return len;
for( int i = 0; i < len ;)
{
index = (int)s[i];
temp = arr[index];
//cout<<temp<<" "<<endl;
//注意判断条件
if( temp == -1 || temp < start)
{
arr[index] = i;
count++;
i++;
}
else
{
//在这里做出了优化,注意如何设置count值来避免每次从重复字符处开始探测
max = max > count ? max : count;
//i = temp + 1;
count -= temp-start+1;
start = temp+1;
//memset(arr,-1,sizeof(int)*256);
}
}
max = max > count ? max : count;
return max;
}
};
class Solution {
public:
int lengthOfLongestSubstring(string s)
{
if (s.length()==0)
{
return 0;
}
int t_nMaxLength=1,t_nLength=1;
int t_nRepeatFlag=0;
int t_nNoReaptLength=1;
for (int i=0;i<s.length();i++)
{
int j;
for (j=i+1+t_nNoReaptLength-1;j<s.length();++j)
{
t_nNoReaptLength=0;
for (int k=i;k<j;++k)
{
if (s[k]==s[j])
{
i=k;
t_nRepeatFlag=1;
t_nNoReaptLength=j-k;
break;
}
}
if (t_nRepeatFlag)
{
t_nLength=t_nNoReaptLength;
t_nRepeatFlag=0;
break;
}
else
{
t_nLength++;
if (t_nLength>t_nMaxLength)
{
t_nMaxLength=t_nLength;
}
}
}
if (j==s.length())
{
break;
}
}
return t_nMaxLength;
}
};