无重复字符的最长子串

                                                无重复字符的最长子串

这是我的第一篇博文,创建这个分类是因为个人比较喜欢研究算法,Ok,Talk is cheap,Let's go,I will show you my code.


 

题目描述如下:

给定一个字符串,请你找出其中不含有重复字符的 最长子串 的长度。

示例 1:

输入: "abcabcbb"
输出: 3 
解释: 因为无重复字符的最长子串是 "abc",所以其长度为 3。

示例 2:

输入: "bbbbb"
输出: 1
解释: 因为无重复字符的最长子串是 "b",所以其长度为 1。

示例 3:

输入: "pwwkew"
输出: 3
解释: 因为无重复字符的最长子串是 "wke",所以其长度为 3。
     请注意,你的答案必须是 子串 的长度,"pwke" 是一个子序列,不是子串。


我们来分析一下这个问题,要想找到给定字符串的无重复字符的最长字串的长度,那要对字符串进行遍历,第一种思路是:遍历字符串中的所有字符,并把它们存入set集合中,在存入之前先判断set中是否已经
包含该元素,若包含则返回true,否则返回false,并存入set中。下面我们看下代码:
 1     /**
 2      * 
 3      * @param s 输入的字符串
 4      * @return 最长不重复字串的长度
 5      */
 6     public int lengthOfLongestSubstring(String s) {
 7         int length = s.length();//取得字符串的长度
 8         int size = 0;
 9         for (int i = 0; i < length; i++) {
10             for (int j = i + 1; j <= length; j++) {
11                 if (!isReapt(s, i, j)) {
12                     size = Math.max(size, j - i);
13                 }
14             }
15         }
16         
17         return size;
18     }
19     
20     /**
21      * 
22      * @param s 输入的字符串
23      * @param front 指向字符串的头部
24      * @param rear 指向字符串的尾部
25      * @return 若重复则返回true,否则返回false
26      */
27     public boolean isReapt(String s, int front, int rear) {
28         Set<Character> set = new HashSet();
29         for (int i = front; i < rear; i++) {
30             Character c = s.charAt(i);
31             if (set.contains(c)) {
32                 return true;
33             }
34             set.add(c);
35         }
36         return false;
37     }

 


上面那种解法虽然能解决问题,但过于笨重,那有没有一种办法可以更快呢?答案是有的。我们用到滑块的思想。代码如下:
 1     /**
 2      * 
 3      * @param s 传入的字符串
 4      * @return 最长不重复字串的长度
 5      */
 6     public int lengthOfLongestSubstring(String s) {
 7         int length = s.length();//取得输入字符串的长度
 8         Set<Character> set = new HashSet<>();
 9         int size = 0;
10         int front = 0;//滑块头
11         int rear = 0;//滑块尾
12         while (front < length && rear < length) {
13             
14             if (!set.contains(s.charAt(rear))){//如果set中不包含当前元素,就把它添加到set中,并更新ans值
15                 
16                 set.add(s.charAt(rear++));
17                 size = Math.max(size, rear - front);
18                 
19             }
20             else {
21    
22                 set.remove(s.charAt(front++));//如果set中包含当前元素,就通过逐一移动i的方式删除set内的元素,
23                                           //直到set.contains(s.charAt(j))条件不满足为止
24             }
25         }
26         return size;
27     }



posted @ 2019-04-14 16:53  明说  阅读(166)  评论(0编辑  收藏  举报