双非本科准备秋招(14.1)—— 力扣刷题

news2024/11/19 1:26:03

今天做两个有点难度的题。

1、295. 数据流的中位数

手写堆实现:

        加入元素:

        如何维护一个中位数?我们考虑一下堆的特点,大顶堆堆顶是一个最大值,小顶堆堆顶是一个最小值,那么,如果我们可以把数据流的数据按顺序地平均地存放在两个堆中,一个大顶堆,一个小顶堆,那么大顶堆和小顶堆的堆顶不就是中位数吗?

        就像下图这样,我们依次加入数据流,最后需要形成这样的堆。

        还需要考虑一个问题,我们怎样加入元素?肯定是加一下大顶堆,再加一下小顶堆,这样依次加入元素,但是能直接就加吗?

        不可以的,因为我们的大顶堆需要存储小的那部分元素,小顶堆需要存储大的那部分元素。

        这里需要一个巧妙地操作,比如我们每次要往大顶堆添加元素,先把这个元素加到小顶堆,然后把小顶堆的堆顶加到大顶堆中。

        比如,此时来了个100,两个堆size相同,我们想加到大顶堆中

但是100很大,所以我们先加入小顶堆,然后小顶堆堆顶移到大顶堆

这样就实现了元素加入大顶堆并且大小有序。

加入代码如下:h1大顶堆,h2小顶堆。

        if(h1.size == h2.size){
            h2.offer(num);
            h1.offer(h2.poll());
        }
        else{
            h1.offer(num);
            h2.offer(h1.poll());
        }

        返回答案

          如果元素相同,返回堆头之和除以2;如果不同,那肯定是大顶堆h1多一个元素,直接返回就行。注意结果是double类型。

        if(h1.size == h2.size){
            return (h1.peek() + h2.peek())/2.0;
        }
        return 1.0*h1.peek();

这里我手写一下堆,复习一下堆的基本写法。

 h1 = new Heap(10, true);
 h2 = new Heap(10, false);

第二个参数是true代表大顶堆,是false代表小顶堆,我将大小顶堆代码合并了。

class MedianFinder {
    Heap h1 = null;
    Heap h2 = null;

    public MedianFinder() {
        h1 = new Heap(10, true);
        h2 = new Heap(10, false);
    }
    
    public void addNum(int num) {
        if(h1.size == h2.size){
            h2.offer(num);
            h1.offer(h2.poll());
        }
        else{
            h1.offer(num);
            h2.offer(h1.poll());
        }
    }
    
    public double findMedian() {
        if(h1.size == h2.size){
            return (h1.peek() + h2.peek())/2.0;
        }
        return 1.0*h1.peek();
    }
}
class Heap{
    private int[] array;
    int size;
    Boolean m;

    public Heap(int capacity, Boolean m) {
        this.array = new int[capacity];
        this.m = m;
    }

    public int peek(){
        return size==0 ? -999 : array[0];
    }

    public void offer(int offered){
        if(size == array.length) {
            resize();
        }
        up(offered);
        size++;
    }

    private void resize() {
        int capacity = size + (size>>1);
        int[] newArr = new int[capacity];
        System.arraycopy(array, 0, newArr, 0, size);
        array = newArr;
    }

    private void up(int offered) {
        int child = size;
        while(child > 0){
            int parent = (child - 1) / 2;
            if(m ? offered > array[parent] : offered < array[parent]){
                array[child] = array[parent];
            }
            else {
                break;
            }
            child = parent;
        }
        array[child] = offered;
    }

    public int poll(){
        int top = array[0];
        swap(0, size-1);
        size--;
        down(0);
        return top;
    }

    private void down(int i) {
        int lc = 2*i+1;
        int rc = lc+1;
        int now = i;
        if(lc < size && (m ? array[lc] > array[now] : array[lc] < array[now])){
            now = lc;
        }
        if(rc < size && (m ? array[rc] > array[now] : array[rc] < array[now])){
            now = rc;
        }
        if(now != i){
            swap(now, i);
            down(now);
        }
    }

    private void swap(int top, int bottom) {
        int t = array[top];
        array[top] = array[bottom];
        array[bottom] = t;
    }
}

利用优先队列:

优先队列底层就是堆嘛,所以直接用java提供的优先队列也行。( •̀ ω •́ )y

class MedianFinder {
    PriorityQueue<Integer> q1;
    PriorityQueue<Integer> q2;

    public MedianFinder() {
        q1 = new PriorityQueue<>((o1, o2)->o2-o1);
        q2 = new PriorityQueue<>();
    }
    
    public void addNum(int num) {
        if(q1.size() == q2.size()){
            q2.offer(num);
            q1.offer(q2.poll());
        }
        else{
            q1.offer(num);
            q2.offer(q1.poll());
        }
    }
    
    public double findMedian() {
        return (q1.size()==q2.size() ? 
                    1.0*(q1.peek()+q2.peek())/2 :
                        1.0*q1.peek());
    }
}

2、239. 滑动窗口最大值

        第一想法,直接来个优先队列,但是想想不对,因为优先队列会将窗口中的数据排序,排完序之后窗口继续移动,那我就无法知道应该pop掉哪个元素了。

        我们需要一个数据结构,这个数据结构和队列很像,它能push加入队尾,pop删除队头,getMaxValue获取最大值。但是并没有这种现成的数据结构。

        实现上面需求的数据结构叫做单调队列

        单调队列中存着窗口中的元素,队列头就是当前窗口最大值,为什么能是最大值呢?因为这个队列并不是存储所有的元素,而是有选择的存,单调队列每次新加元素时,都会比较与队尾的值,如果队尾小,就一直pop,直到能添加进去,所以,如果此时新加的元素是最大值,那么它会pop掉所有队元素,成为队头。

        所以,想要在单调队列中存活,需要满足两个条件:

  • 在窗口的范围内
  • 没有被新来的元素干掉,也就是不比新来的元素小

        java中,我使用LinkedList,LinkedList实现了双端队列接口,用双端队列来模拟单调队列。

class Solution {
    public int[] maxSlidingWindow(int[] nums, int k) {
        LinkedList<Integer> list = new LinkedList<>();
        //nums.length-k+1
        int len = nums.length;
        int[] ans = new int[len-k+1];
        int cnt = 0;
        for(int i = 0; i < len; i++){
            //弹出过时的
            while(!list.isEmpty() && list.peek() < i-k+1){
                list.poll();
            }
            //弹出末尾不够大的
            while(!list.isEmpty() && nums[list.peekLast()] < nums[i]){
                list.pollLast();
            }
            list.offer(i);
            if(i >= k-1){
                ans[cnt++] = nums[list.peek()];
            }
        }

        return ans;
    }
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1428441.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

R语言学习case7:ggplot基础画图(核密度图)

step1: 导入ggplot2库文件 library(ggplot2)step2&#xff1a;带入自带的iris数据集 iris <- datasets::irisstep3&#xff1a;查看数据信息 dim(iris)维度为 [150,5] head(iris)查看数据前6行的信息 step4&#xff1a;画图展示 plot2 <- ggplot(iris,aes(Sepal.W…

踩坑STM32CubeMX生成Makefile工程无法使用printf(“%f“)

过去一年偶有接触STM32开发时都是使用STM32CubeMX生成Makefile的工程&#xff0c;具体开发环境见配置Clion用于STM32开发&#xff08;Makefile&#xff09;&#xff0c;但没想到今天在使用printf打印输出浮点数时无法正常输出&#xff0c;不仅printf无法使用&#xff0c;其他涉…

024 增强for循环

什么是增强for循环 用法 int[] arr {1,3,5,7,9}; for (int i : arr) {System.out.println(i); } 拓展 增强for不止用于数组&#xff0c;还可以用于集合。 增强for是for的偷懒写法&#xff0c;必定可以被for的写法的代替&#xff0c;但for不一定会被增强for代替。

【详细教程】Kubernetes集群部署:使用kubeadm创建集群

文章目录 一、虚拟机准备&#xff08;一&#xff09;主机基本配置&#xff08;二&#xff09;安装docker&#xff08;三&#xff09;配置cri-docker环境&#xff08;四&#xff09;安装kubeadm、kubelet、kubectl&#xff08;五&#xff09;克隆主机 二、环境配置工作&#xff…

扫盲软件开发工具低代码

目录 一、低代码是什么&#xff1f; 二、低代码平台的优势和劣势都是什么&#xff1f; 三、低代码操作方式 四、写在最后 一、低代码是什么&#xff1f; 低代码是一套可视化开发工具&#xff0c;它帮开发者把前后端基础功能写扎实&#xff0c;开发者只需要通过填表配置或拖…

Java SWT Composite 绘画

Java SWT Composite 绘画 1 Java SWT2 Java 图形框架 AWT、Swing、SWT、JavaFX2.1 Java AWT (Abstract Window Toolkit)2.2 Java Swing2.3 Java SWT (Standard Widget Toolkit)2.4 Java JavaFX 3 比较和总结 1 Java SWT Java SWT&#xff08;Standard Widget Toolkit&#xff…

3593 蓝桥杯 查找最大元素 简单

3593 蓝桥杯 查找最大元素 简单 // C风格解法1&#xff0c;通过率100%&#xff0c;多组数据处理样式//str "abcdefgfedcba" //abcdefg(max)fedcba//str "xxxxx" //x(max)x(max)x(max)x(max)x(max)#include<bits/stdc.h>const int N 1e2 10;char …

pdf怎么改成word文档?PDF转Word的方法

Word是一种常用的文字处理软件&#xff0c;具有丰富的编辑功能。通过将PDF转换成Word&#xff0c;您可以轻松地对文档进行编辑、修改和格式调整。这对于需要对文本进行更改、添加或删除内容的情况非常有用&#xff0c;本文介绍一个pdf转word的简单方法&#xff0c;通过压缩图的…

Qt加载网页崩溃 ASSERT:“m_adapterClient“ in file ...

1、软件启动后加载网页无异常&#xff0c;点击按钮&#xff0c;加载新网页时崩溃 崩溃代码&#xff1a; QWebEngineView *createWindow(QWebEnginePage::WebWindowType type) { Q_UNUSED(type); return this; } 2、原因 Qt只是调用谷歌的浏览器引擎&#xff…

Python爬虫某云免费音乐——多线程批量下载

重点一&#xff1a;每首音乐的下载地址 重点二&#xff1a;如何判断是免费音乐 重点三&#xff1a;如何用线程下载并保存 重点四&#xff1a;如何规避运行错误导致子线程死掉 重点五&#xff1a;如何管理子线程合理运行 需要全部代码的私信或者VX:Kmwcx1109 运行效果&…

【机器学习】AAAI 会议论文聚类分析

实验五&#xff1a;AAAI 会议论文聚类分析 ​ 本次实验以AAAI 2014会议论文数据为基础&#xff0c;要求实现或调用无监督聚类算法&#xff0c;了解聚类方法。 1 任务介绍 ​ 每年国际上召开的大大小小学术会议不计其数&#xff0c;发表了非常多的论文。在计算机领域的一些大…

vue实现el-table-column中自定义label

默认的label只能显示普通文字&#xff0c;如果有一些特殊需求&#xff0c;比如换行显示&#xff0c;更改文字颜色&#xff0c;更改文字大小&#xff0c;就需要自定义label了 <el-table-column label"组合" align"center" key"combinData" pr…

element表格内多个输入框时如何添加表单校验

以下.vue文件Demo可直接复制运行&#xff1a; 重点&#xff1a; 1&#xff1a;表格数据定义在form里 2&#xff1a;prop需要加索引&#xff1b;索引前的变量不要加form&#xff0c;直接取里边的key&#xff0c;索引后的字段需要和表格里字段属性对应 。:prop"tableInfo.l…

华为数通方向HCIP-DataCom H12-821题库(单选题:381-400)

第381题 以下是某台设备通过display isis lsdb命令输出的信息,那么关于以上输出的信息的描述,正确的是哪一项? <R1>display isis lsdbDatabase information for ISIS(1)--------------------------------Level-1 Link State DatabaseLSPID Seq Num…

【Linux】环境基础开发工具的使用之gcc详解(二)

前言&#xff1a;上一篇文章中我们讲解了Linux下的vim和yum的工具的使用&#xff0c;今天我们将在上一次的基础上进一步的讲解开放工具的时候。 &#x1f496; 博主CSDN主页:卫卫卫的个人主页 &#x1f49e; &#x1f449; 专栏分类:Linux的深度刨析 &#x1f448; &#x1f4a…

[Python] 什么是逻辑回归模型?使用scikit-learn中的LogisticRegression来解决乳腺癌数据集上的二分类问题

什么是线性回归和逻辑回归&#xff1f; 线性回归是一种用于解决回归问题的统计模型。它通过建立自变量&#xff08;或特征&#xff09;与因变量之间的线性关系来预测连续数值的输出。线性回归的目标是找到一条直线&#xff08;或超平面&#xff09;&#xff0c;使得预测值与观…

WhisperFusion:与 AI 无缝语音对话(超低延迟),深入理解用户每句话背后的含义

演示视频里面&#xff0c;那老哥问它问题之后&#xff0c;后面更改问题&#xff0c;依然能很好的记录问题变化的过程并给出答案。 WhisperFusion 是基于 WhisperLive 和 WhisperSpeech 的强大工具&#xff0c;将声音转文字和文字理解融为一体&#xff0c;让你与AI机器人无缝语…

Linux-----文本三剑客补充~

一、模糊匹配 模糊匹配用 ~ 表示包含&#xff0c;!~表示不包含 1、匹配含有root的列 [rootlocalhost ~]#awk -F: /root/ /etc/passwd root:x:0:0:root:/root:/bin/bash operator:x:11:0:operator:/root:/sbin/nologin [rootlocalhost ~]#awk -F: $1~ /root/ /etc/passw…

网工内推 | 港企、合资公司,厂商认证优先,五险一金

01 九龙仓&#xff08;长沙&#xff09;置业有限公司 招聘岗位&#xff1a;IT网络工程师 职责描述&#xff1a; 1.负责公司网络架构规划设计、设备选型、远程组网方案的规划和设计&#xff1b; 2.负责公司网络IP地址规划管理&#xff0c;根据业务需求和公司状况&#xff0c;对…

将有逻辑关系的树形结构数组转换为扁平化的一维对象数组(包含PID、ID父子关系)(tree转换为List)

// 将有逻辑关系的树形结构数组转换为扁平化的一维对象数组 treeStructure2flatArray(arr) {let r [], r_ (ar, PID root) > ar.forEach(v > (v.children && (r_(v.children, v.ID), delete v.children), (v.PID PID, r.push(v))));r_(JSON.parse(JSON.strin…