zoukankan      html  css  js  c++  java
  • Longest Substring Without Repeating Characters -- LeetCode

    原题链接: http://oj.leetcode.com/problems/longest-substring-without-repeating-characters/ 
    这道题用的方法是在LeetCode中很常用的方法,对于字符串的题目非常有用。 首先brute force的时间复杂度是O(n^3), 对每个substring都看看是不是有重复的字符,找出其中最长的,复杂度非常高。优化一些的思路是稍微动态规划一下,每次定一个起点,然后从起点走到有重复字符位置,过程用一个HashSet维护当前字符集,认为是constant操作,这样算法要进行两层循环,复杂度是O(n^2)。 

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

    public int lengthOfLongestSubstring(String s) {  
        if(s==null || s.length()==0)  
            return 0;  
        HashSet<Character> set = new HashSet<Character>();  
        int max = 0;  
        int walker = 0;  
        int runner = 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++;  
            }  
            else  
            {  
                set.add(s.charAt(runner));  
            }  
            runner++;  
        }  
        max = Math.max(max,runner-walker);  
        return max;  
    }  

    这道题思想在字符串处理的题中还是比较重要的,实现上主要是HashSet和数组index的操作。扩展的题目有Substring with Concatenation of All WordsMinimum Window Substring,思路是非常接近的,只是操作上会更加繁琐一些。

  • 相关阅读:

    泛型
    特性
    2.Linux基础入门
    1.Linux介绍及系统安装
    php十七种设计模式适用场合总结
    转载zendframework 插件方式
    常用的Jquery代码片段,没事的时候研究一下
    Zend Framework1.9 模块化搭建
    PHP的设计模式总结命令链模式
  • 原文地址:https://www.cnblogs.com/scarecrow-blog/p/6062247.html
Copyright © 2011-2022 走看看