代码随想录算法训练营第十三天|239. 滑动窗口最大值、347.前 K 个高频元素

239. 滑动窗口最大值

题目链接;239. 滑动窗口最大值
思路:设计一个单调递减队列,出口元素为当前窗口最大值。设计单调队列的时候,pop,和push操作要保持如下规则:

  • pop(value):如果窗口移除的元素value等于单调队列的出口元素,那么队列弹出元素,否则不用任何操作
  • push(value):如果push的元素value大于入口元素的数值,那么就将队列入口的元素弹出,直到push元素的数值小于等于队列入口元素的数值为止

保持如上规则,每次窗口移动的时候,只要问que.front()就可以返回当前窗口的最大值。
代码如下:

from collections import deque


class Myqueue:
    def __init__(self):
        self.queue = deque()

    def pop(self, value: int):
        if self.queue and value == self.queue[0]:
            self.queue.popleft()

    def push(self, value: int):
        while self.queue and value > self.queue[-1]:
            self.queue.pop()
        self.queue.append(value)

    def front(self):
        return self.queue[0]


class Solution:
    def maxSlidingWindow(self, nums: List[int], k: int) -> List[int]:
        que = Myqueue()
        result = []
        for i in range(k):
            que.push(nums[i])
        result.append(que.front())
        for i in range(k, len(nums)):
            que.pop(nums[i - k])
            que.push(nums[i])
            result.append(que.front())
        return result
  • 时间复杂度: O(n)
  • 空间复杂度: O(k)

学习时长
30分钟

347.前 K 个高频元素

题目链接:347.前 K 个高频元素
思路:这道题目主要涉及到如下三块内容:要统计元素出现频率、对频率排序、找出前K个高频元素。首先统计元素出现的频率,这一类的问题可以使用map来进行统计。然后我们要用小顶堆对部分频率进行排序 ,因为要统计最大前k个元素,只有小顶堆每次将最小的元素弹出,最后小顶堆里积累的才是前k个最大元素。因为小顶堆先弹出的是最小的,所以倒序来输出到数组。
代码如下:

import heapq
class Solution:
    def topKFrequent(self, nums: List[int], k: int) -> List[int]:
        map_ = {}
        for num in nums:
            map_[num] = map_.get(num,0)+1
        pri_que = []
        for key,freq in map_.items():
            heapq.heappush(pri_que,(freq,key))
            if len(pri_que) > k:
               heapq.heappop(pri_que)
        result = [0]*k
        for i in range(k-1,-1,-1):
            result[i] = heapq.heappop(pri_que)[1]
        return result

  • 时间复杂度:O(nlogk)
  • 空间复杂度:O(n)

学习时长
40分钟

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值