Longest Substring Without Repeating Characters

给定一个字符串,找到其中的一个最长的字串,使得这个子串不包含重复的字符。

基本思路是维护一个窗口,每次关注窗口中的字符串,在每次判断中,左窗口和右窗口选择其一向前移动。同样是维护一个HashSet, 正常情况下移动右窗口,如果没有出现重复则继续移动右窗口,如果发现重复字符,则说明当前窗口中的串已经不满足要求,继续移动有窗口不可能得到更好的结果,此时移动左窗口,直到不再有重复字符为止,中间跳过的这些串中不会有更好的结果,因为他们不是重复就是更短。因为左窗口和右窗口都只向前,所以两个窗口都对每个元素访问不超过一遍,因此时间复杂度为O(2*n)=O(n),是线性算法。空间复杂度为HashSet的size,也是O(n). 代码如下:

public static int lengthOfLongestSubstring(String s) {
    	
    	if(s==null || s.length()==0)  
            return 0;  
    	
    	ArrayList<Character> set=new ArrayList<Character>();
    	int max=1;
    	int runner=0;
    	int walker=0;
    	while(runner<s.length()){
    		if(set.contains(s.charAt(runner))){//如果集合中包含该元素
    			if(max<runner-walker){
    				max=runner-walker;
    			}
    			
    			while(s.charAt(walker)!=s.charAt(runner)){
    				set.remove(s.charAt(walker));
    				walker++;
    			}	
    			walker++;//以上的while循环和这个++就是移动左边的窗口,使得窗口内的元素不重复
    		}
    		else {//如果不包含
				set.add(s.charAt(runner));
			}
    		runner++;
    	}
    	max=Math.max(max, runner-walker);//很重要
        return max;
    }


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值