Leetcode 340 最长最多K个无重复字符的字符串长度

题目

Given a string, find the length of the longest substring T that contains at most k distinct characters.java

For example, Given s = “eceba” and k = 2,web

T is “ece” which its length is 3.svg

快慢指针 + HashMap

通常这种题目都是采用一个快慢 pointer来作spa

  • 慢指针指向第一个起始位置 ,如今要决定的是何时更新慢指针pre指针

  • 快指针指向当前的处理位置 icode

当前的可能长度就是i - pre + 1的长度状况xml

思考为什么要使用while 循环包裹在外面的状况token

代码

public class longest {
    public int solution(String s, int  k){
        if(s==null ||k<1)
            return 0;
        if(s.length()<k)
            return s.length();
        Map<Character, Integer> map =new HashMap<>();
        int pre =0;
        int result =k;

        for(int i=0;i<s.length();i++){

			//好比当前的处理元素是b, map.put(s.charAt(i),map.getOrDefault(s.charAt(i),0)+1);

           处理到当前合适位置的状况吧,状况 eceb   处理成为 eb 知足k=2; 
            while(map.size()>k){
                char p =s.charAt(pre++);
                int count = map.get(p);
                count--;
                if(count==0)
                {
                    map.remove(p);
                }
                else
                {
                    map.put(p,count);
                }

            }

            result =Math.max(result,i-pre+1);
        }
        return result;

    }

    public static void main(String[] args) {
        longest test =new longest();
        System.out.println(test.solution("ececbac",2));
    }

}

案例

在处理 ece 以前不用进行while(map.size()>k)这段代码的处理流程状况,rem

eceb 第一次while处理 后变成 ceb, 而后进入第二次处理流程的状况get

eb 处理成为这样状况 最后 pre 变成了 2, 3-2+1 最大的长度为2 因此仍是不知足该种状况

p

快慢指针

public class Solution {
    public int lengthOfLongestSubstringKDistinct(String s, int k) {
        if (s == null || s.length() == 0 || k <= 0) {
            return 0;
        }
        HashMap<Character, Integer> map = new HashMap<Character, Integer>();
        int count = 0;
        int start = 0;
        int max = 0;
        for (int i = 0; i < s.length(); i++) {
            char c = s.charAt(i);
            if (map.containsKey(c)) {
                map.put(c, map.get(c) + 1);
            } else {
                map.put(c, 1);
                // 若是是第一次put的有可能
                while (map.size() > k) {
                    char rm = s.charAt(start);
                    int tempCount = map.get(rm);
                    if (tempCount > 1) {
                        map.put(rm, tempCount - 1);
                    } else {
                        map.remove(rm);
                    }
                    start++;
                   //
                    count--;
                }
            }
            count++;
            max = Math.max(max, count);
        }
        return max;
    }
}