Skip to content

Files

Latest commit

aca34c1 · Mar 3, 2023

History

History
183 lines (142 loc) · 5.04 KB

File metadata and controls

183 lines (142 loc) · 5.04 KB

English Version

题目描述

您将获得一个 从0开始的 整数数组 candies ,其中 `candies[i]`表示第 i 个糖果的味道。你妈妈想让你和你妹妹分享这些糖果,给她 k连续 的糖果,但你想保留尽可能多的糖果口味。
在与妹妹分享后,返回 最多 可保留的 独特 口味的糖果。

 

示例 1:

输入: candies = [1,2,2,3,4,3], k = 3
输出: 3
解释:
将[1,3](含[2,2,3])范围内的糖果加入[2,2,3]口味。
你可以吃各种口味的糖果[1,4,3]。
有3种独特的口味,所以返回3。

示例 2:

输入: candies = [2,2,2,2,3,3], k = 2
输出: 2
解释:
在[3,4]范围内(含[2,3])的糖果中加入[2,3]口味。
你可以吃各种口味的糖果[2,2,2,3]。
有两种独特的口味,所以返回2。
请注意,你也可以分享口味为[2,2]的糖果,吃口味为[2,2,3,3]的糖果。

示例 3:

输入: candies = [2,4,5], k = 0
输出: 3
解释:
你不必给任何糖果。
你可以吃各种口味的糖果[2,4,5]。
有3种独特的口味,所以返回3。

 

提示:

  • 1 <= candies.length <= 105
  • 1 <= candies[i] <= 105
  • 0 <= k <= candies.length

解法

方法一:滑动窗口 + 哈希表

我们可以维护一个大小为 k 的滑动窗口,窗口外的糖果为自己的,窗口内的 k 个糖果分给妹妹和妈妈。我们可以用哈希表 c n t 记录窗口外的糖果口味以及对应的数量。

初始时,哈希表 c n t 中存储的是 c a n d i e s [ k ] c a n d i e s [ n 1 ] 的糖果口味以及对应的数量。此时糖果口味的种类数为哈希表 c n t 的大小,即 a n s = c n t . s i z e ( )

接下来,我们遍历 [ k , . . n 1 ] 范围内的糖果,将当前糖果 c a n d i e s [ i ] 加入窗口内,同时将窗口左侧的糖果 c a n d i e s [ i k ] 移出窗口外。然后我们更新哈希表 c n t ,并且更新糖果口味的种类数 a n s m a x ( a n s , c n t . s i z e ( ) )

遍历完所有糖果后,我们即可得到最多可保留的独特口味的糖果。

时间复杂度 O ( n ) ,空间复杂度 O ( n ) 。其中 n 为糖果的数量。

Python3

class Solution:
    def shareCandies(self, candies: List[int], k: int) -> int:
        cnt = Counter(candies[k:])
        ans = len(cnt)
        for i in range(k, len(candies)):
            cnt[candies[i]] -= 1
            cnt[candies[i - k]] += 1
            if cnt[candies[i]] == 0:
                cnt.pop(candies[i])
            ans = max(ans, len(cnt))
        return ans

Java

class Solution {
    public int shareCandies(int[] candies, int k) {
        Map<Integer, Integer> cnt = new HashMap<>();
        int n = candies.length;
        for (int i = k; i < n; ++i) {
            cnt.merge(candies[i], 1, Integer::sum);
        }
        int ans = cnt.size();
        for (int i = k; i < candies.length; ++i) {
            if (cnt.merge(candies[i], -1, Integer::sum) == 0) {
                cnt.remove(candies[i]);
            }
            cnt.merge(candies[i - k], 1, Integer::sum);
            ans = Math.max(ans, cnt.size());
        }
        return ans;
    }
}

C++

class Solution {
public:
    int shareCandies(vector<int>& candies, int k) {
        unordered_map<int, int> cnt;
        int n = candies.size();
        for (int i = k; i < n; ++i) {
            ++cnt[candies[i]];
        }
        int ans = cnt.size();
        for (int i = k; i < candies.size(); ++i) {
            if (--cnt[candies[i]] == 0) {
                cnt.erase(candies[i]);
            }
            ++cnt[candies[i - k]];
            ans = max(ans, (int) cnt.size());
        }
        return ans;
    }
};

Go

func shareCandies(candies []int, k int) (ans int) {
	cnt := map[int]int{}
	for _, c := range candies[k:] {
		cnt[c]++
	}
	ans = len(cnt)
	for i := k; i < len(candies); i++ {
		cnt[candies[i]]--
		if cnt[candies[i]] == 0 {
			delete(cnt, candies[i])
		}
		cnt[candies[i-k]]++
		ans = max(ans, len(cnt))
	}
	return
}

func max(a, b int) int {
	if a > b {
		return a
	}
	return b
}

TypeScript

...