1. 程式人生 > >LeetCode 697. Degree of an Array

LeetCode 697. Degree of an Array

一、問題描述

    Given a non-empty array of non-negative integers nums, the degree of this array is defined as the maximum frequency of any one of its elements.

    Your task is to find the smallest possible length of a (contiguous) subarray of nums, that has the same degree as nums.

Example1

Input: [1, 2, 2, 3, 1]
Output: 2
Explanation: 
The input array has a degree of 2 because both elements 1 and 2 appear twice.
Of the subarrays that have the same degree:
[1, 2, 2, 3, 1], [1, 2, 2, 3], [2, 2, 3, 1], [1, 2, 2], [2, 2, 3], [2, 2]
The shortest length is 2. So return 2.

Example2

Input: [1,2,2,3,1,4,2]
Output: 6

二、題意分析

陣列的degree定義為:最多重複元素個數。 我們的任務是找到陣列的一個子集(連續的),它的degree和輸入陣列的degree相等,且子集中元素的個數最少。

三、解題思路

需要統計陣列中每一個數重複出現的次數,因此使用Map儲存key出現的次數;此外,我們還需要在degree相同的子集中,找出元素個數最少的子集,因此,我們還需要儲存key在輸入陣列中開始索引和結束的索引,以方便計運算元集長度。

  1. 統計出每個key對應的個數:<key, appears>, 每個key開始的索引和結束的索引:<fromIndex, endIndex>;
  2. 根據輸入陣列的degree帥選出滿足條件的key;
  3. 計算出元素個數最少的子集。

程式碼實現

public int findShortestSubArray(int[] nums) {
    if(nums.length < 2)
        return nums.length;
    Map<Integer, Integer> keyAppears = new HashMap<>();
    Map<Integer, Integer[]> keyAppearsIndex = new HashMap<>();
    int degree = 1, degree_index = 0, counts = 0;
    Integer[] indexs;
    for(int i = 0 ; i < nums.length; i++){
        if(keyAppears.get(nums[i]) == null){
            keyAppears.put(nums[i], 1);
            indexs= new Integer[2];
            indexs[0] = i;
            keyAppearsIndex.put(nums[i], indexs);
        }else{
            counts = keyAppears.get(nums[i]);
            keyAppears.put(nums[i], counts+1);
            // 輸入陣列的degree
            // degree = Math.max(degree, counts+1);
            if(degree < counts+1){
                degree = counts+1;
                degree_index = nums[i];
            }
            keyAppearsIndex.get(nums[i])[1] = i;
        }

    }
    if(degree == 1)
        return degree;
    indexs = keyAppearsIndex.get(degree_index);
    int minLen = indexs[1] - indexs[0] + 1; 
    // 獲取輸入陣列的degree 
    for(Map.Entry<Integer, Integer> entry: keyAppears.entrySet()){
        if(entry.getValue() != degree)
            continue;
        indexs = keyAppearsIndex.get(entry.getKey());
        minLen = Math.min(minLen, indexs[1] - indexs[0] + 1);
    }
    return minLen;
}

時間、空間複雜度分析

  1. 時間複雜度

O (n)

  1. 空間複雜度

O(n)

在這裡插入圖片描述