隨緣記錄 LeetCode第168場周賽 2019-12-22

5292. 劃分數組爲連續數字的集合

給你一個整數數組 nums 和一個正整數 k,請你判斷是否能夠把這個數組劃分紅一些由 k 個連續數字組成的集合。
若是能夠,請返回 True;不然,返回 False。java

示例 1:
輸入:nums = [1,2,3,3,4,4,5,6], k = 4
輸出:true
解釋:數組能夠分紅 [1,2,3,4] 和 [3,4,5,6]。

**題目表述爲集合,不是數組。 =__=**數組

輸入:nums = [3,3,2,2,1,1], k = 3
輸出:true

分析:ide

須要將數組按照k個一組劃分。因此一共有len / k 個集合。若是不能整除說明不符合條件。code

由於考慮到是集合,因此先將數組進行排序。排序

  • 首先用map統計每一個數字纔出現的次數。
  • 而後遍歷數組的每一個元素。
    • 從map中取出每一個元素的出現次數。若是數量爲0,說明該元素已經被包含到其餘的集合啦,能夠跳過了。
      • 每取出一個元素,就能夠將保存的個數-1。
    • 而後就開始查詢符合條件的集合。
      • 從map中分別取出num+i的元素剩餘次數,i從1到len / k
      • 若是次數爲0,說明當前的這一個集合不符合條件。返回false
    • 寫到這裏已經能夠獲得結果。可是在後序的查詢過程當中可能存在不少已經將數量減小到0的元素。
      • 爲了減小後序操做,定義一個變量m。維護已經出現的符合條件的集合的次數。若是m等於len/k,說明已經找到了所有符合條件的集合返回true;
public boolean isPossibleDivide(int[] nums, int k) {
    int len = nums.length;
    if(len%k!=0){
        return false;
    }
    Arrays.sort(nums);
    Map<Integer,Integer> map = new HashMap<>();
    for(int num:nums){
        map.put(num,map.getOrDefault(num,0)+1);
    }
    int count = len/k;
    int m = 0;
    for(int num:nums){
        int start = map.get(num);
        if(start==0){
            //已經沒有了
            continue;
        }
        map.put(num,start-1);
        for(int i =1;i<k;i++){
            int temp = map.getOrDefault(num+i,0);
            if(temp==0){
                //當前序列不合法。
                return false;
            }
            map.put(num+i,temp-1);
        }
        m++;
        if(m==count){
            return true;
        }
    }
    return true;
}

5293. 子串的最大出現次數

給你一個字符串 s ,請你返回知足如下條件且出現次數最大的 任意 子串的出現次數:leetcode

子串中不一樣字母的數目必須小於等於 maxLetters
子串的長度必須大於等於 minSize 且小於等於 maxSize字符串

輸入:s = "aababcaab", maxLetters = 2, minSize = 3, maxSize = 4
輸出:2
解釋:子串 "aab" 在原字符串中出現了 2 次。
它知足全部的要求:2 個不一樣的字母,長度爲 3 (在 minSize 和 maxSize 範圍內)。

這道題須要尋找的是知足條件的出現次數最大的任意子串的次數。get

  • 雖然給定了最大和最小長度,實際上只須要使用最小的長度就能計算處出現的最大次數。
  • 在計算出現次數的基礎上,題目須要保證子串字母數量小於等於maxLetter,固然使用Set結合計算數量。若是不符合條件就捨棄當前子串。
  • 爲了保證在串s長度極長的狀況下不會超時。可使用Map保存每一個串出現的次數。
  • 在遍歷結束後,統計集合中出現的最大次數,即爲結果。
public int maxFreq(String s, int maxLetters, int minSize, int maxSize) {
    char[] arr= s.toCharArray();
    Map<String,Integer> map = new HashMap<>();
    for(int i =0;i<=s.length()-minSize;i++){
        if(checkOut(arr,i,i+minSize-1)<=maxLetters){
            String key = String.valueOf(arr,i,minSize);
            map.put(key,map.getOrDefault(key,0)+1);
        }
    }
    int count = 0;
    for(Integer num : map.values()){
        count = count<num ?num:count;
    }
    return count;
}
public int checkOut(char[] arr,int start,int end){
    Set<Character> set = new HashSet<>();
    for(int i =start;i<=end;i++){
        set.add(arr[i]);
    }
    return set.size();
}
相關文章
相關標籤/搜索