LeetCode 378 有序矩阵中第K小的元素

news2024/11/18 16:33:26

题目信息

LeetoCode地址: . - 力扣(LeetCode)

题解内容大量转载于:. - 力扣(LeetCode)

题目理解

题意很直观,就是求二维矩阵中所有元素排序后第k小的数。

最小堆写法

该写法不再赘述,维护一个大小为k的小顶堆,遍历矩阵所有元素进行入堆操作。

时间复杂度:O(nlogk)

空间复杂度:O(k)

class Solution {
    public int kthSmallest(int[][] matrix, int k) {
        PriorityQueue<Integer> heap = new PriorityQueue<>((a,b) -> (int)b-(int)a);
        for (int i = 0; i<matrix.length; i++) {
            for (int j = 0; j<matrix[0].length;j++) {
                if (heap.size() < k) {
                    heap.offer(matrix[i][j]);
                } else if (matrix[i][j] < heap.peek()) {
                    heap.poll();
                    heap.offer(matrix[i][j]);
                }
            }
        }
        return heap.peek();

    }
}

二分写法

由于矩阵在行和列上都是有序的,因此左上角的元素matrix[0][0]一定是最小的,右下角的元素matrix[n-1][n-1]一定是最大的。这两个元素,我们分别记为l 和 r.

以下图为例:

可以发现, 任取一个数mid满足l<=mid<=r, 那么矩阵中不大于mid的数,肯定都分布在矩阵的左上角。

例如下图, 取mid=8:

我们可以看出,矩阵中大于mid的数和不大于mid的数分别形成了两个版本,沿着一条锯齿线将这个矩形分隔开。其中左上角板块的大小即为不大于mid的数的数量。

我们只需沿着这条锯齿线走一遍即可计算出这两个板块的大小,自然就统计出这个矩阵中不大于mid的数的个数了。

同样以mid=8举例,走法如下:

走法可以总结如下:

  • 初始位置在matrix[n-1][0] (即左下角);
  • 设当前位置为matrix[i][j], 若matrix[i][j] <= mid, 则将当前所在列的不大于mid的数的数量(即i+1)累加到答案中,并向右移动,否则向上移动;
  • 不断移动,直到走出格子为止。

可以发现,这样的走法时间复杂度为O(n),即我们可以线性的计算对于任意一个mid,矩阵中有多少数不大于它。这满足了二分查找的性质。

不妨设答案为x, 那么可以直到l<=x<=r, 这样就确定了二分查找的上下界。

对于每次猜测的答案mid, 计算矩阵中有多少数不大于 mid:

  • 如果数量不少于k, 那么说明最终答案不大于mid;
  • 如果数量小于k, 那么说明最终答案大于mid.

这样我们就可以计算出最终的结果x了。

时间复杂度: O(nlogn)

额外空间复杂度: O(1)

class Solution {
    public int kthSmallest(int[][] matrix, int k) {
        int h = matrix.length, w = matrix[0].length;
        int l = matrix[0][0], r = matrix[h-1][w-1];
        while (l < r) {
            int mid = l + (r-l)/2;
            if (check(matrix, mid, k)) {
                r = mid;
            } else {
                l = mid+1;
            }
        }
        return l;
    }
    public boolean check(int[][] matrix,int mid, int k) {
        int i = matrix.length-1, j = 0;
        int count = 0;
        while (i >=0 && j < matrix[0].length) {
            if (matrix[i][j] <= mid) {
                count += i+1;
                j++;
            } else {
                i--;
            }
        }
        return count >= k; 
    }
}

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

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

相关文章

好看流光风格个人主页HTML源码

这是一款好看流光风格个人主页HTML源码&#xff0c;感觉挺喜欢的&#xff0c;需要的自行下载&#xff01; 源码下载 好看流光风格个人主页源码

“进击的巨人”:服务器硬件基础知识解析

引言&#xff1a; 服务器是网络环境中负责处理数据、运行应用程序和服务多用户的高性能计算机系统。了解服务器的硬件构成有助于更好地管理和优化IT资源。 服务器和普通PC的差异&#xff1a; 服务器具有比个人电脑更高的处理能力、稳定性和可靠性&#xff0c;它们通常运行在没…

【JavaEE】浅谈线程(一)

线程 前言线程的由来线程是什么线程的属性线程更高效的原因举个例子&#xff08;线程便利性的体现&#xff09; 多线程代码线程并发执行的代码jconsole(观测多线程) 线程的调度问题创建线程的几种方法1&#xff09;通过继承Thread 重写run2&#xff09;使用Runnable接口 重写ru…

.NET8 和 Vue.js 的前后端分离

在.NET 8中实现前后端分离主要涉及到两个部分&#xff1a;后端API的开发和前端应用的开发。后端API通常使用ASP.NET Core来构建&#xff0c;而前端应用则可以使用任何前端框架或技术栈&#xff0c;比如Vue.js、React或Angular等。下面是一个简化的步骤指南&#xff0c;帮助你在…

指针 基础知识

本笔记为观看56 指针-指针的定义和使用_哔哩哔哩_bilibili后的学习笔记 指针的定义和使用 1、定义指针 int main () {//1、定义指针int a 10;//指针定义的语法&#xff1a; 数据类型 * 指针变量名&#xff1b;int * p;//让指针记录变量a的地址p &a; //& 为取址符cou…

Mac资源库的东西可以删除吗?mac资源库在哪里打开 cleanmymacx是什么 cleanmymac免费下载

在使用Mac电脑的过程中&#xff0c;用户可能会遇到存储空间不足的问题。一种解决方法是清理不必要的文件&#xff0c;其中资源库&#xff08;Library&#xff09;文件夹是一个常被提及但又让人迷惑的目标。Mac资源库的东西可以删除吗&#xff1f;本文旨在解释Mac资源库的作用、…

Java常用函数接口

Java常用函数接口 Java 8 中引入的常用函数式接口&#xff0c;也就是 java.util.function 包中的接口。这些接口提供了一种简洁的方式来定义函数&#xff0c;常用于 Lambda 表达式和方法引用。下面是一些常用的接口&#xff1a; 一、Predicate&#xff08;断言&#xff09; …

应用性能分析工具CPU Profiler

简介 本文档介绍应用性能分析工具CPU Profiler的使用方法&#xff0c;该工具为开发者提供性能采样分析手段&#xff0c;可在不插桩情况下获取调用栈上各层函数的执行时间&#xff0c;并展示在时间轴上。 开发者可通过该工具查看TS/JS代码及NAPI代码执行过程中的时序及耗时情况…

c语言之动态内存管理及常见错误分析,柔性数组,内存划分

目录 前言 一&#xff1a;malloc,calloc,realloc,free四大函数 1.malloc 2.free 3.calloc 4.realloc 二&#xff1a;常见错误分析 1.malloc返回值不检查直接使用 2.对动态开辟空间的越界访问 3.对非动态开辟空间free 4.使用free释放动态开辟内存的一部分 5.对…

QAuth 2.0

OAuth 2.0授权框架支持第三方支持访问有限的HTTP服务&#xff0c;通过在资源所有者和HTTP服务之间进行一个批准交互来代表资源者去访问这些资源&#xff0c;或者通过允许第三方应用程序以自己的名义获取访问权限。 为了方便理解&#xff0c;可以想象OAuth2.0就是在用户资源和第…

多路转接-epoll/Reactor(2)

epoll 上次说到了poll&#xff0c;它存在效率问题&#xff0c;因此出现了改进的poll----epoll。 目前epoll是公认的效率最高的多路转接的方案。 快速了解epoll接口 epoll_create&#xff1a; 这个参数其实已经被废弃了。 这个值只要大于0就可以了。 这是用来创建一个epoll模…

用友U9 存在PatchFile.asmx接口任意文件上传漏洞

声明&#xff1a; 本文仅用于技术交流&#xff0c;请勿用于非法用途 由于传播、利用此文所提供的信息而造成的任何直接或者间接的后果及损失&#xff0c;均由使用者本人负责&#xff0c;文章作者不为此承担任何责任。 简介 用友U9是由中国用友软件股份有限公司开发的一款企业…

FJSP:狐猴优化算法(Lemurs Optimizer,LO)求解柔性作业车间调度问题(FJSP),提供MATLAB代码

一、柔性作业车间调度问题 柔性作业车间调度问题&#xff08;Flexible Job Shop Scheduling Problem&#xff0c;FJSP&#xff09;&#xff0c;是一种经典的组合优化问题。在FJSP问题中&#xff0c;有多个作业需要在多个机器上进行加工&#xff0c;每个作业由一系列工序组成&a…

Linux(Ubuntu)中创建【samba】服务,用于和Windows系统之间共享文件

目录 1.先介绍一下什么是Samba 2.安装&#xff0c;配置服务 安装 配置&#xff08;smb.conf&#xff09; 配置用户 3.出现的问题&#xff08;Failed to add entry for user XXXX&#xff09; 4.创建文件夹 5.windows访问 1.先介绍一下什么是Samba Samba是一个开源的软…

HTML5.Canvas简介

1. Canvas.getContext getContext(“2d”)是Canvas元素的方法&#xff0c;用于获取一个用于绘制2D图形的绘图上下文对象。在给定的代码中&#xff0c;首先通过getElementById方法获取id为"myCanvas"的Canvas元素&#xff0c;然后使用getContext(“2d”)方法获取该Ca…

剑指Offer题目笔记26(动态规划的基础知识)

面试题88&#xff1a; 问题&#xff1a; ​ 一个数组cost的所有数字都是正数&#xff0c;它的第i个数字表示在一个楼梯的第i级台阶往上爬的成本&#xff0c;在支付了成本cost[i]之后可以从第i级台阶往上爬1级或2级。请计算爬上该楼梯的最少成本。 解决方案一&#xff1a;&…

【简单讲解下epoll】

&#x1f3a5;博主&#xff1a;程序员不想YY啊 &#x1f4ab;CSDN优质创作者&#xff0c;CSDN实力新星&#xff0c;CSDN博客专家 &#x1f917;点赞&#x1f388;收藏⭐再看&#x1f4ab;养成习惯 ✨希望本文对您有所裨益&#xff0c;如有不足之处&#xff0c;欢迎在评论区提出…

Day:004(1) | Python爬虫:高效数据抓取的编程技术(数据解析)

数据解析-正则表达式 在前面我们已经搞定了怎样获取页面的内容&#xff0c;不过还差一步&#xff0c;这么多杂乱的代码夹杂文字我们怎样 把它提取出来整理呢&#xff1f;下面就开始介绍一个十分强大的工具&#xff0c;正则表达式&#xff01; 正则表达式是对字符串操作的一种…

力扣Lc28---- 557. 反转字符串中的单词 III(java版)-2024年4月06日

1.题目描述 2.知识点 1)用StringBuilder的方法 实现可变字符串结果 最后返回的时候用.toString的方法 2)在Java中使用StringBuilder的toString()方法时&#xff0c;它会返回StringBuilder对象当前包含的所有字符序列的字符串表示。 在我们的例子中&#xff0c;sb是一个Stri…

Django之五种中间件定义类型—process_request、process_view、process_response.......

目录 1. 前言 2. 基础中间件 3. 如何自定义中间件 4. 五种自定义中间件类型 4.1 process_request 4.2 process_view 4.3 process_response 4.4 process_exception 4.5 process_template_response 5. 最后 1. 前言 哈喽&#xff0c;大家好&#xff0c;我是小K,今天咋们…