CodeTop之數組中的第K個最大的元素

題目鏈接

215. 數組中的第K個最大元素 - 力扣(LeetCode)

題目解析

算法原理

解法一:

直接理由java內部的排序函數,Arrays.sort()進行排序, 然后我們直接返回第k個最大的元素

nums[nums.length-k]

解法二:

使用堆

我們先把所有元素丟到大根堆里面,然后取k次堆頂元素

PriorityQueue<Integer> heap = new PriorityQueue<>((a,b)->b-a);

解法三:?

三指針法, 數組分三塊

代碼編寫

解法一:

class Solution {public int findKthLargest(int[] nums, int k) {// 排序Arrays.sort(nums);return nums[nums.length - k];}
}

解法二:

class Solution {public int findKthLargest(int[] nums, int k) {// 利用大根堆PriorityQueue<Integer> heap = new PriorityQueue<>((a,b)-> b-a);// 把元素放進大根堆for(int x : nums){heap.offer(x);}// 取第k個while(--k != 0){heap.poll();}return heap.poll();}
}

解法三

class Solution {// 交換private static void swap(int[] nums, int index1, int index2) {int tmp = nums[index1];nums[index1] = nums[index2];nums[index2] = tmp;}// 遞歸,分三段private static int quickSort(int[] nums, int l, int r, int k) {// l, r 是用來固定左右端點的int left = l - 1;int right = r + 1;// 獲取區間中間的元素作為 keyint key = nums[(l + r) / 2];  // 修改這里,取中間的值// 數組分成四段// [l,left]<key,[left+1,i]==key,[i+1,right-1]未知,[right,r]>key;int i = l;  // 從區間的開始進行遍歷while (i < right) {// 如果是 < keyif (nums[i] < key) {swap(nums, ++left, i++);} else if (nums[i] == key) {// 如果是 == keyi++;} else {// 如果是 > keyswap(nums, --right, i);}}// 此時分成三塊: [l, left]<key [left + 1, right - 1]==key [right, r]>key// 分類討論 [l, left] [left + 1, right - 1] [right, r]int b = (right - 1) - (left + 1) + 1;  // 中間部分的長度int c = r - right + 1;  // [right, r] 部分的長度if (c >= k) {// 去 [right, r] 查找第 k 大return quickSort(nums, right, r, k);} else if ((b + c) >= k) {// 如果中間部分就是第 k 大,直接返回return key;} else {// 去 [l, left] 查找第 k - b - c 大return quickSort(nums, l, left, k - b - c);}}public int findKthLargest(int[] nums, int k) {return quickSort(nums, 0, nums.length - 1, k);}
}

為什么是k-b-c大? 下面是ai的解釋
在快速排序(Quick Sort)中,我們通過分區操作將數組分為三部分:

1.小于基準值(key)的部分
2.等于基準值的部分
3.大于基準值的部分

我們希望找到第 k 大的元素。在快速排序的過程中,我們每次選擇一個基準值(key)并進行分區,接下來,我們遞歸地在其中一部分繼續查找目標元素。
問題核心
假設我們有一個 k 值,表示我們要找到第 k 大的元素。在分區后,數組被分為三部分:

[l, left] 這部分元素都小于基準值 key
[left + 1, right - 1] 這部分元素等于基準值 key
[right, r] 這部分元素都大于基準值 key

我們已經知道,在這些分區中,key 的位置非常關鍵。接下來,我們就要根據 k 和這些部分的大小來決定遞歸的方向。
代碼邏輯解釋
考慮下面幾個變量:

b:等于 key 的元素的個數。
c:大于 key 的元素的個數。

那么,b + c 是右邊部分(即大于 key 的部分加上等于 key 的部分)的元素總數。
如果 k 大于 b + c,意味著我們要找的第 k 大的元素不在右邊(即大于 key 的部分和等于 key 的部分),而是在左邊(小于 key 的部分)。因此,我們遞歸地去左邊查找。
但是,左邊的部分有一些特殊情況需要考慮:

左邊的部分包含了所有小于 key 的元素,因此找第 k 大的元素時,要跳過這些小于 key 的元素。
1由于已經知道有 b 個元素等于 key,而且右邊有 c 個大于 key 的元素,所以我們實際需要在左邊找的是第 k - b - c 大的元素。

為什么是 k - b - c

我們已經知道:
c 是大于 key 的元素數量。

b 是等于 key 的元素數量。
因此,如果我們要找的是第 k 大的元素,在遞歸調用時,要在左邊查找的是:
去掉 c 個大于 key 的元素,
去掉 b 個等于 key 的元素,
所以我們要查找的是 第 k - b - c 大的元素。

總結

k 是我們要找的第 k 大的元素。
b 是等于 key 的元素個數。
c 是大于 key 的元素個數。

因此,在左邊查找時,我們要尋找的元素是第 k - b - c 大的元素,原因是我們已經排除了右邊部分的元素(大于 key 和等于 key 的部分)。

二刷

class Solution {//交換void swap(int[] nums, int index1, int index2) {int tmp = nums[index1];nums[index1] = nums[index2];nums[index2] = tmp;}int quickSort(int[] nums, int l, int r, int k) {// 定義移動邊界int left = l - 1;int right = r + 1;int key = nums[(right + left) / 2];// 遍歷int i = l;while (i < right) {// 數組分四塊if (nums[i] < key) {// 去左邊swap(nums, i++, ++left);} else if (nums[i] == key) {// 直接往后走i++;} else {// 去右邊swap(nums, i, --right);}}// 此時分為三塊:[l,left]<key [left+1,right-1]=key [right,r]>key// 去找第k個最大的元素int b = (right - 1) - (left + 1) + 1; //中間部分int c = r - right + 1; // 右邊部分if (c >= k) {// 說明第k個最大在右邊部分return quickSort(nums, right, r, k);} else if ((b + c) >= k) {// 說明第k個最大在中間部分return key;} else {// 說明第k個最大在左邊部分,調整kreturn quickSort(nums, l, left, k - b - c);}}public int findKthLargest(int[] nums, int k) {// 使用快排來找到數組中第k個最大元素return quickSort(nums, 0, nums.length - 1, k);}
}


?

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/pingmian/82849.shtml
繁體地址,請注明出處:http://hk.pswp.cn/pingmian/82849.shtml
英文地址,請注明出處:http://en.pswp.cn/pingmian/82849.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

AI任務相關解決方案1-基于NLP的3種模型實現實體識別,以及對比分析(包括基于規則的方法、CRF模型和BERT微調模型)

大家好,我是微學AI,今天給大家介紹一下AI任務相關解決方案1-基于NLP的3種模型實現實體識別,以及對比分析。本文將深入探討三種不同的命名實體識別(NER)方法,包括基于規則的方法、CRF模型和BERT微調模型,用于識別文本中的地名(LOC)、機構名稱(ORG)和人名(PER)實體。通過系統…

IP動態偽裝開關

IP動態偽裝開關 在OpenWrt系統中&#xff0c;IP動態偽裝&#xff08;IP Masquerading&#xff09;是一種網絡地址轉換&#xff08;NAT&#xff09;技術&#xff0c;用于在私有網絡和公共網絡之間轉換IP地址。它通常用于允許多個設備共享單個公共IP地址訪問互聯網。以下是關于O…

【MySQL】第10節|MySQL全局優化與Mysql 8.0新增特性詳解

全局優化 mysql server參數 1. max_connections&#xff08;最大連接數&#xff09; 含義&#xff1a;MySQL 服務允許的最大并發連接數&#xff08;包括正在使用和空閑的連接&#xff09;。超過此限制時&#xff0c;新連接會被拒絕&#xff08;報錯 Too many connections&am…

VS Code 插件 Git History Diff

插件名 進命令行&#xff0c;進Git自己那個分支 查看分支 提交到Git的后想再把另一個也提交到那個分支&#xff0c;用這個命令

Shell腳本中的常用命令

一.設置主機名稱 文件設置 文件開機時已讀取所以要重新進入 命令更改&#xff08;即使生效&#xff09; 二.網絡管理命令 1.查看網卡命令 設置網卡 1&#xff09;DHCP工作模式 2)靜態IP 3&#xff09;修改網卡信息 三.簡單處理字符 1.打印連續數字 連續打印3個數字 指定打…

C++ 中 std::wstring::c_str() 的潛在風險與安全使用指南

一、問題背景 在開發過程中&#xff0c;我們經常會遇到不同接口之間的數據傳遞問題。例如&#xff0c;當調用某個接口時&#xff0c;需要傳入一個字符串指針作為數據接收的緩沖區&#xff0c;但外圍接口使用的是 std::wstring 類型。此時&#xff0c;如果直接將 std::wstring:…

‘js@https://registry.npmmirror.com/JS/-/JS-0.1.0.tgz‘ is not in this registry

解決方法&#xff1a; 1. npm cache clean --force 2.臨時切換到官方源 npm config set registry https://registry.npmjs.org/ npm install js0.1.0 npm config set registry https://registry.npmmirror.com/ # 切換回鏡像源

ubuntu24 安裝MongoDB-6.0.24 數據庫操作步驟和配置參數說明

目錄 1 下載MongoDB軟件 2 操作系統信息 3 MongoDB 軟件安裝步驟 4 編寫mongodb的配置文件 5 生成keyfile 6 使用mongo用戶啟動mongodb服務 7 設置開機啟動(mongo用戶) 8 安裝MongoDB shell&#xff0c;因為MongoDB-6.0.24 已經移除mongo命令 1 下載MongoDB軟件 https:…

單片機——keil5

文章目錄 安裝教程使用介紹案例展示 接下來進行keil5軟件的相關學習使用 安裝教程 參考視頻鏈接bilibili 51單片機 大約在8分鐘位置處 使用介紹 首先新建project選擇對應的芯片型號&#xff08;例如&#xff1a;STC89C52 —— 由于STC系列是國產&#xff0c;keil5軟件不支持…

計算機網絡相關發展以及常見性能指標

目錄 一、因特網概述 1.1 基本概念 1.2 因特網發展的三個階段 1.3 英特網服務提供者ISP 1.4 英特網的標準化工作 1.5 因特網的組成 1.6 簡單總結 二、3種交換方式 2.1 電路交換&#xff08;Circuit Switching&#xff09; 2.2 分組交換&#xff08;Packet Switching&…

Java 面試實錄:從Spring到微服務的技術探討

在一個明亮的會議室里&#xff0c;嚴肅的面試官與搞笑的程序員謝飛機正進行一場關于Java技術棧的面試。場景設定在一家知名互聯網大廠&#xff0c;他們的對話充滿了技術性與娛樂性。 第一輪&#xff1a;Spring框架與數據庫 面試官&#xff1a;“謝飛機&#xff0c;能解釋一下…

OpenCV CUDA模塊圖像過濾------創建一個 Scharr 濾波器函數createScharrFilter()

操作系統&#xff1a;ubuntu22.04 OpenCV版本&#xff1a;OpenCV4.9 IDE:Visual Studio Code 編程語言&#xff1a;C11 算法描述 該函數用于創建一個 Scharr 濾波器&#xff08;基于 CUDA 加速&#xff09;&#xff0c;用于圖像的一階導數計算。它常用于邊緣檢測任務中&#…

yolov8分割任務的推理和后處理解析

文章目錄 一、前言二、分割模型的前向推理1. 檢測結果&#xff1a;來自Detect類的輸出2. 分割結果&#xff08;最終&#xff09;3. 與Detect的主要區別4. 工作流程 三、后處理1. 非極大值抑制&#xff08;NMS&#xff09;過濾檢測框2. 分割原型&#xff08;Mask Prototypes&…

4.1.1 Spark SQL概述

Spark SQL是Apache Spark的一個模塊&#xff0c;專門用于處理結構化數據。它引入了DataFrame這一編程抽象&#xff0c;DataFrame是帶有Schema信息的分布式數據集合&#xff0c;類似于關系型數據庫中的表。用戶可以通過SQL、DataFrames API和Datasets API三種方式操作結構化數據…

華為OD機試真題——書籍疊放(2025A卷:200分)Java/python/JavaScript/C/C++/GO最佳實現

2025 A卷 200分 題型 本專欄內全部題目均提供Java、python、JavaScript、C、C++、GO六種語言的最佳實現方式; 并且每種語言均涵蓋詳細的問題分析、解題思路、代碼實現、代碼詳解、3個測試用例以及綜合分析; 本文收錄于專欄:《2025華為OD真題目錄+全流程解析+備考攻略+經驗分…

尚硅谷redis7 63-69 redis哨兵監控之理論簡介

63 redis哨兵監控之理論簡介 什么是哨兵 master掛了如何辦?從機原地待命。此時數據只能讀取不能更新。因此需要&#xff1a; 吹哨人巡查監控后臺master主機是否故障,如果故障了根據投票數自動將某一個從庫轉換為新主庫, 哨兵的作用 1、監控redis運行狀態,包括master和slave…

word文檔格式規范(論文格式規范、word格式、論文格式、文章格式、格式prompt)

文章目錄 prompt prompt [格式要求] - 字體&#xff1a;中文宋體小四&#xff1b;英文Times New Roman 12pt&#xff1b;標題黑體 - 行距&#xff1a;1.5倍&#xff08;段前段后0行&#xff09; - 邊距&#xff1a;A4默認&#xff08;上下2.54cm&#xff0c;左右3.17cm&…

SpringBoot+tabula+pdfbox解析pdf中的段落和表格數據

一、前言 在日常業務需求中&#xff0c;往往會遇到解析pdf文件中的段落或者表格數據的需求。 常見的做法是使用 pdfbox 來做&#xff0c;但是它只能提取文本數據&#xff0c;沒有我們在文件頁面上面的那種結構化組織&#xff0c;文本通常是散亂的包含各種換行回車空格等格式&a…

【Elasticsearch】stored_fields

在 Elasticsearch 中&#xff0c;stored_fields 是一個非常重要的概念&#xff0c;主要用于控制文檔存儲和檢索時的行為。以下是對 stored_fields 的詳細解釋&#xff1a; 1\. stored_fields 的作用 stored_fields 用于指定在檢索文檔時需要返回的字段。默認情況下&#xff0c;…

計算機網絡 | 1.1 計算機網絡概述思維導圖

附大綱&#xff1a; 計算機網絡的概念 一個通過通信設備與線路把不同計算機系統連接起來&#xff0c;實現資源共享和信息傳遞的系統 計算機網絡的組成 從組成成分上 硬件&#xff1a;主機、通信鏈路、交換設備、通信處理機軟件&#xff1a;網絡操作系統、聊天軟件等協議&…