双非本科准备秋招(13.1)—— 力扣 栈、队列与堆

1、103. 二叉树的锯齿形层序遍历

昨天做的二叉树的层序遍历,把代码直接拿过来。

这个题要求的是一个Z型遍历,如下图。

        用一个变量f记录正反顺序,然后使用LinkedList记录答案,下图可以看到LinkedList继承了Deque,所以可以当作双端队列来用。

每次记录答案时,根据f的值选择调用offerLast和offerFirst方法。

class Solution {
    public List<List<Integer>> zigzagLevelOrder(TreeNode root) {
        LinkedBlockingQueue<TreeNode> q = new LinkedBlockingQueue<>();
        List<List<Integer>> list = new ArrayList<>();
        if(root == null) return list;
        q.offer(root);
        int cnt = 1;
        boolean f = true;

        while(!q.isEmpty()){
            LinkedList<Integer> L = new LinkedList<>();
            int temp = 0;
            for(int i = 0; i < cnt; i++){
                TreeNode t = q.poll();
                if(f) L.offerLast(t.val);
                else L.offerFirst(t.val);
                if(t.left != null){
                    q.offer(t.left);
                    temp++;
                }
                if(t.right != null){
                    q.offer(t.right);
                    temp++;
                }
            }
            cnt = temp;
            list.add(L);
            f = !f;
        }

        return list;
    }
}

2、23. 合并 K 个升序链表

        用优先队列来做,默认排序即可(小顶堆),最后处理一下答案,把队列q中的元素转移到新的链表上。

class Solution {
    public ListNode mergeKLists(ListNode[] lists) {
        PriorityQueue<Integer> q = new PriorityQueue<>();
        ListNode head = new ListNode();
        ListNode p = head;
        for(int i = 0; i < lists.length; i++){
            while(lists[i] != null){
                q.offer(lists[i].val);
                lists[i] = lists[i].next;
            }
        }
        while(!q.isEmpty()){
            ListNode t = new ListNode(q.poll());
            p.next = t;
            p = p.next;
        }
        return head.next;
    }
}

3、215. 数组中的第K个最大元素

堆这种数据结构就适合求前几个具有xx特性的元素问题,包括下一个题目和最后一个题目。

这个题用小顶堆做,我们可以手写一个堆的结构class MinHeap。

我们只需要把前k个元素加入堆(offer()方法),然后后面的元素只需要判断是否大于堆中的第一个元素即可,如果大于,就替换第一个元素(replace()方法)。

因为堆中第一个元素是k个中最小的,我们不断加入大的元素,那么最后是不是堆中只剩下最大的k个元素了,k个最大元素中最小的不就是堆的第一个元素嘛。

class Solution {
    public int findKthLargest(int[] nums, int k) {
        MinHeap heap = new MinHeap(k);

        for(int i = 0; i < k; i++){
            heap.offer(nums[i]);
        }

        for(int i = k; i < nums.length; i++){
            if(nums[i] > heap.array[0]){
                heap.replace(nums[i]);
            }
        }

        return heap.array[0];
    }
}

public class MinHeap {
    int[] array;
    int size;

    public MinHeap(int capacity) {
        this.array = new int[capacity];
    }

    public void offer(int offerd){
        up(offerd);
        size++;   
    }

    public void up(int offerd){
        int child = size;
        while(child > 0){
            int parent = (child-1)/2;
            if(array[parent] > offerd){
                array[child] = array[parent];
            }
            else{
                break;
            }
            child = parent;
        }
        array[child] = offerd;
    }

    public void replace(int replaced){
        array[0] = replaced;
        down(0);
    }

    private void down(int parent) {
        int lc = parent*2+1;
        int rc = lc+1;
        int min = parent;
        if(lc < size && array[lc] < array[min]){
            min = lc;
        }
        if(rc < size && array[rc] < array[min]){
            min = rc;
        }
        if(min != parent){
            swap(min, parent);
            down(min);
        }
    }

    private void swap(int i, int j) {
        int t = array[i];
        array[i] = array[j];
        array[j] = t;
    }
}

4、703. 数据流中的第 K 大元素

与上个题不能说一模一样,只能说完全一致。

需要注意add方法要判断一下堆是不是满了,因为初始化堆的时候有可能提供的元素个数小于k个,如果没满直接加入堆就好。

class KthLargest {
    MinHeap heap = null;
    public KthLargest(int k, int[] nums) {
        heap = new MinHeap(k);
        int len = Math.min(k, nums.length);
        for(int i = 0; i < len; i++){
            heap.offer(nums[i]);
        }
        for(int i = k; i < nums.length; i++){
            if(nums[i] > heap.array[0]){
                heap.replace(nums[i]);
            }
        }
    }
    
    public int add(int val) {
        if(heap.size < heap.array.length){
            heap.offer(val);
        }
        else if(val > heap.array[0]){
            heap.replace(val);
        }
        return heap.array[0];
    }
}

public class MinHeap {
    int[] array;
    int size;

    public MinHeap(int capacity) {
        this.array = new int[capacity];
        Arrays.fill(this.array, Integer.MIN_VALUE);
    }

    public void offer(int offerd){
        up(offerd);
        size++;   
    }

    public void up(int offerd){
        int child = size;
        while(child > 0){
            int parent = (child-1)/2;
            if(array[parent] > offerd){
                array[child] = array[parent];
            }
            else{
                break;
            }
            child = parent;
        }
        array[child] = offerd;
    }

    public void replace(int replaced){
        array[0] = replaced;
        down(0);
    }

    private void down(int parent) {
        int lc = parent*2+1;
        int rc = lc+1;
        int min = parent;
        if(lc < size && array[lc] < array[min]){
            min = lc;
        }
        if(rc < size && array[rc] < array[min]){
            min = rc;
        }
        if(min != parent){
            swap(min, parent);
            down(min);
        }
    }

    private void swap(int i, int j) {
        int t = array[i];
        array[i] = array[j];
        array[j] = t;
    }
}

5、1047. 删除字符串中的所有相邻重复项

解释:
例如,在 "abbaca" 中,我们可以删除 "bb" 由于两字母相邻且相同,这是此时唯一可以执行删除操作的重复项。之后我们得到字符串 "aaca",其中又只有 "aa" 可以执行重复项删除操作,所以最后的字符串为 "ca"。

读完解释后,感觉就是明示了栈的数据结构。

我们把a入栈,b入栈,b入栈,b和栈顶重复,b不入了并且弹出栈顶元素,这时候栈只剩下a,然后a入栈,a和栈顶重复,a不入了并且弹出栈顶元素,栈空了,然后c入栈,a入栈。

这时候我们依次弹出,得到ac,那么我们可以倒着遍历字符串,倒着入栈,结果都是一样的,不影响删除相邻重复的字母。

class Solution {
    public String removeDuplicates(String s) {
        Stack<Character> stack = new Stack<>();
        for(int i = s.length()-1; i >= 0; i--){
            if(!stack.isEmpty() && stack.peek() == s.charAt(i)){
                stack.pop();
            }
            else{
                stack.push(s.charAt(i));
            }
        }
        String ans = "";
        while(!stack.isEmpty()){
            ans += stack.pop();
        }

        return ans;
    }
}

6、347. 前 K 个高频元素

        元素与元素的次数,让人联想到哈希表。存到哈希表后,对出现的次数进行排序,这应该是第一思路。

        前k个高频元素,有出现了前几个具有xx特性的这种要求,我们就会想到堆,在堆中只存放前k个高频元素,使用小顶堆,我们最后得到的就是前k个最高频的元素了。

        java中的ProrityQueue的底层就是堆,我就不用自己写的了。因为我们的堆中要存储数据和出现的次数,因此可以存个数组,下标0代表是什么数据,下标1代表出现的次数。        

        我们先加入到map中,然后遍历map集合,把cnt大于堆顶的元素替换掉原来的元素,也就是队列出队,这样就得到了前k个高频的元素了。

class Solution {
    public int[] topKFrequent(int[] nums, int k) {
        PriorityQueue<int[]> q = new PriorityQueue<>(k, (o1, o2) -> o1[1] - o2[1]);
        HashMap<Integer, Integer> map = new HashMap<>();

        for(int i = 0; i < nums.length; i++){
            int v = 0;
            if(map.containsKey(nums[i])){
                v = map.get(nums[i]);
            }
            map.put(nums[i], v+1);
        }

        for(Integer n : map.keySet()){
            int cnt = map.get(n);
            if(q.size() < k){
                q.offer(new int[]{n, cnt});
            }
            else if(cnt > q.peek()[1]){
                q.poll();
                q.offer(new int[]{n, cnt});
            }
        }

        int[] ans = new int[k];
        int j = 0;
        while(!q.isEmpty()){
            ans[j++] = q.poll()[0];
        }
        return ans;
    }
}

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

k8s二进制及负载均衡集群部署详解

目录 常见部署方式 二进制部署流程 环境准备 操作系统初始化配置 关闭防火墙 配置SELinux 关闭SWAP 根据规划设置主机名 在master添加hosts&#xff0c;便于主机名解析 调整内核参数 配置时间同步 部署docker引擎 在所有node节点部署docker引擎 部署etcd集群 签发…

【文本到上下文 #8】NLP中的变形金刚:解码游戏规则改变者

一、说明 欢迎来到我们对不断发展的自然语言处理 &#xff08;NLP&#xff09; 领域的探索的第 8 章。在本期中&#xff0c;我们将重点介绍一项重塑 NLP 格局的突破性创新&#xff1a;Transformers。在我们之前对 seq2seq 模型、编码器-解码器框架和注意力机制的讨论之后&#…

flutter如何实现省市区选择器

前言 当我们需要用户填写地址时&#xff0c;稳妥的做法是让用户通过“滚轮”来滑动选择省份&#xff0c;市&#xff0c;区&#xff0c;此文采用flutter的第三方库来实现这一功能&#xff0c;比调用高德地图api简单一些。 流程 选择库 这里我选择了一个最近更新且支持中国的…

ABAP Range Table:RANGES的使用

目录 Range TableRANGERANGES RANGE的四个参数SIGNOPTIONLOWHIGH示例程序 Range Table 1、Range Table 概述 RANGE TABLE为 SAP R/3系统标准内表的一种&#xff0c;结构与 Selection Table 一致&#xff0c; 由 SIGN, OPTION, LOW 和 HIGH字段组成&#xff1b; 可以通过 TYPE…

面试宝典之深谈JVM

面试宝典之深谈JVM 1.为什么需要JVM&#xff0c;不要JVM可以吗&#xff1f; 1.JVM可以帮助我们屏蔽底层的操作系统 一次编译&#xff0c;到处运行 2.JVM可以运行Class文件 2.JDK&#xff0c;JRE以及JVM的关系 3.我们的编译器到底干了什么事&#xff1f; 仅仅是将我们的 .ja…

【动态规划】【C++算法】1340. 跳跃游戏 V

作者推荐 【动态规划】【字符串】【表达式】2019. 解出数学表达式的学生分数 本文涉及知识点 动态规划汇总 LeetCode1340跳跃游戏 V 给你一个整数数组 arr 和一个整数 d 。每一步你可以从下标 i 跳到&#xff1a; i x &#xff0c;其中 i x < arr.length 且 0 < x…

用户界面(UI)、用户体验(UE)和用户体验(UX)的差异

对一个应用程序而言&#xff0c;UX/UE (user experience) 设计和 UI (user interface) 设计非常重要。UX设计包括可视化布局、信息结构、可用性、图形、互动等多个方面。UI设计也属于UX范畴。正是因为三者在一定程度上具有重叠的工作内容&#xff0c;很多从业多年的设计师都分不…

2024年美国大学生数学建模A题思路分析 - 资源可用性和性别比例

# 1 赛题 问题A&#xff1a;资源可用性和性别比例 虽然一些动物物种存在于通常的雄性或雌性性别之外&#xff0c;但大多数物种实质上是雄性或雌性。虽然许多物种在出生时的性别比例为1&#xff1a;1&#xff0c;但其他物种的性别比例并不均匀。这被称为适应性性别比例的变化。…

STM32CubeIDE 使用标准库来编写程序

这些天我想找一个软件来实现软件的替代。就找到了st 的生态。可是现在st 生态都在极力的推荐HAL 库,但是习惯了标准库的朋友们,还不是很习惯。 先上总结一下,为了好记忆: 一、 在编译栏做如下设置 1、头文件设置 2、源文件设置 二、指定具体的预定义宏 1、USE_STDPERIPH_D…

angular 表单FormGroup笔记

一、校验 1、校验提示 <nz-form-item><nz-form-label>手机号码</nz-form-label><nz-form-control [nzErrorTip]"mobileTemplate"><input nz-input formControlName"mobile" placeholder"请输入" /><ng-templ…

【Java并发】聊聊Disruptor背后高性能的原理

为什么需要Disruptor 对于单机生产者消费者来说&#xff0c;JUC本身提供了阻塞队列&#xff0c;ArrayBlockingQueue、LinkedBlockingQueue 等&#xff0c;但是为了保证数据安全&#xff0c;使用了reentrantLock进行加锁操作会影响性能&#xff0c;另一方面&#xff0c;本身如果…

正点原子--STM32中断系统学习笔记(1)

1、什么是中断&#xff1f; 原子哥给出的概念是这样的&#xff1a;打断CPU正常执行的程序&#xff0c;转而处理紧急程序&#xff0c;然后返回原暂停的程序继续运行&#xff0c;就叫中断。 当发生中断时&#xff0c;当前执行的程序会被暂时中止&#xff0c;进而进入中断处理函…

05:容器镜像技术揭秘|发布容器服务器|私有镜像仓库

容器镜像技术揭秘&#xff5c;发布容器服务器&#xff5c;私有镜像仓库 创建镜像使用commit方法创建自定义镜像。Dockerfile打包镜像创建apache服务镜像制作 php 镜像 微服务架构创建nginx镜像 发布服务通过映射端口发布服务容器共享卷 docker私有仓库 创建镜像 使用commit方法…

Hadoop3.x基础(3)- MapReduce

来源: B站尚硅谷 目录 MapReduce概述MapReduce定义MapReduce优缺点优点缺点 MapReduce核心思想MapReduce进程常用数据序列化类型MapReduce编程规范WordCount案例实操本地测试提交到集群测试 Hadoop序列化序列化概述自定义bean对象实现序列化接口&#xff08;Writable&#xff…

Nicn的刷题日常之BC68 X形图案

1.题目描述 KiKi学习了循环&#xff0c;BoBo老师给他出了一系列打印图案的练习&#xff0c;该任务是打印用“*”组成的X形图案。 输入描述&#xff1a; 多组输入&#xff0c;一个整数&#xff08;2~20&#xff09;&#xff0c;表示输出的行数&#xff0c;也表示组成“X”的反斜…

推荐一款嵌入式系统自动化测试工具(可免费试用)

本文介绍一款对嵌入式系统进行全面自动化测试的工具&#xff0c;不需要自己做任何开发&#xff0c;就可以在项目测试中直接使用起来&#xff0c;支持对各类嵌入式系统进行全面自动化测试。 嵌入式系统一般是产品的核心单元&#xff0c;嵌入式系统是否可靠决定了整个产品的质量…

【域适应十五】Universal Domain Adaptation through Self-Supervision

1.motivation 传统的无监督域自适应方法假设所有源类别都存在于目标域中。在实践中,对于这两个领域之间的类别重叠可能知之甚少。虽然有些方法使用部分或开放集类别处理目标设置,但它们假设特定设置是已知的先验设置。本文提出了一个更普遍适用的领域自适应框架,可以处理任…

【leetcode热题100】编辑距离

给你两个单词 word1 和 word2&#xff0c; 请返回将 word1 转换成 word2 所使用的最少操作数 。 你可以对一个单词进行如下三种操作&#xff1a; 插入一个字符删除一个字符替换一个字符 示例 1&#xff1a; 输入&#xff1a;word1 "horse", word2 "ros&qu…

政安晨的机器学习笔记——演绎一个TensorFlow官方的Keras示例(对服装图像进行分类,很全面)

导语 Keras是一个高级API接口&#xff0c;用于构建和训练神经网络模型。它是TensorFlow的一部分&#xff0c;提供了一种简洁、直观的方式来创建深度学习模型。 Keras的主要特点如下&#xff1a; 简洁易用&#xff1a;Keras提供了一组简单的函数和类&#xff0c;使模型的创建和…