13-跳躍游戲 II

給定一個長度為?n?的?0 索引整數數組?nums。初始位置為?nums[0]

每個元素?nums[i]?表示從索引?i?向后跳轉的最大長度。換句話說,如果你在?nums[i]?處,你可以跳轉到任意?nums[i + j]?處:

  • 0 <= j <= nums[i]?
  • i + j < n

返回到達?nums[n - 1]?的最小跳躍次數。生成的測試用例可以到達?nums[n - 1]

方法一:?貪心算法

這是一個典型的貪心算法問題,要求計算到達數組最后一個位置的最小跳躍次數。以下是使用 TypeScript 實現的代碼:

代碼實現

function jump(nums: number[]): number {const n = nums.length;if (n === 1) {return 0;}// 當前跳躍能到達的最遠位置let currentMaxReach = 0;// 下一步跳躍能到達的最遠位置let nextMaxReach = 0;// 跳躍次數let jumps = 0;for (let i = 0; i < n - 1; i++) {// 更新下一步跳躍能到達的最遠位置nextMaxReach = Math.max(nextMaxReach, i + nums[i]);// 如果當前位置到達了當前跳躍能到達的最遠位置if (i === currentMaxReach) {// 進行一次跳躍jumps++;// 更新當前跳躍能到達的最遠位置為下一步跳躍能到達的最遠位置currentMaxReach = nextMaxReach;// 如果當前跳躍能到達的最遠位置已經可以到達數組的最后一個位置,直接返回跳躍次數if (currentMaxReach >= n - 1) {break;}}}return jumps;
}// 示例調用
const nums = [2, 3, 1, 1, 4];
const minJumps = jump(nums);
console.log("到達數組最后一個位置的最小跳躍次數:", minJumps);

代碼解釋

  1. 邊界條件處理:如果數組長度為 1,說明已經在最后一個位置,不需要跳躍,直接返回 0。
  2. 初始化變量
    • currentMaxReach:表示當前跳躍能到達的最遠位置,初始化為 0。
    • nextMaxReach:表示下一步跳躍能到達的最遠位置,初始化為 0。
    • jumps:表示跳躍次數,初始化為 0。
  3. 遍歷數組
    • 在遍歷過程中,不斷更新?nextMaxReach,它是當前位置?i?加上該位置能跳躍的最大長度?nums[i]?與之前的?nextMaxReach?中的較大值。
    • 當?i?等于?currentMaxReach?時,說明已經到達了當前跳躍能到達的最遠位置,此時需要進行一次跳躍,jumps?加 1。
    • 同時更新?currentMaxReach?為?nextMaxReach,表示進入下一次跳躍的范圍。
    • 如果?currentMaxReach?已經大于等于數組的最后一個位置的索引?n - 1,說明已經可以到達最后一個位置,直接跳出循環。
  4. 返回結果:遍歷結束后,jumps?即為到達數組最后一個位置的最小跳躍次數,將其返回。

復雜度分析

  • 時間復雜度:O(n),其中??是數組的長度。因為只需要對數組進行一次遍歷。
  • 空間復雜度:O(1),只使用了常數級的額外變量。

這種貪心算法的核心思想是在每一次跳躍中,盡可能地跳到最遠的位置,從而用最少的跳躍次數到達數組的最后一個位置。

方法二:?廣度優先搜索

除了前面介紹的貪心算法,還可以使用廣度優先搜索(BFS)的方法來解決這個問題。BFS 的核心思想是從起始位置開始,逐層擴展所有可能的跳躍位置,直到到達目標位置,每擴展一層就相當于進行了一次跳躍,記錄擴展的層數即為最小跳躍次數。

代碼實現

function jump(nums: number[]): number {const n = nums.length;if (n === 1) {return 0;}// 記錄已經訪問過的位置const visited = new Array(n).fill(false);// 初始化隊列,隊列中存儲 [當前位置, 跳躍次數]const queue: [number, number][] = [[0, 0]];visited[0] = true;while (queue.length > 0) {const [currentIndex, jumps] = queue.shift()!;// 遍歷當前位置能跳躍到的所有位置for (let j = 1; j <= nums[currentIndex] && currentIndex + j < n; j++) {const nextIndex = currentIndex + j;// 如果到達了最后一個位置,返回當前跳躍次數加 1if (nextIndex === n - 1) {return jumps + 1;}// 如果該位置未被訪問過if (!visited[nextIndex]) {// 標記為已訪問visited[nextIndex] = true;// 將該位置和跳躍次數加 1 加入隊列queue.push([nextIndex, jumps + 1]);}}}return -1; // 理論上不會執行到這里,因為題目保證可以到達最后一個位置
}// 示例調用
const nums = [2, 3, 1, 1, 4];
const minJumps = jump(nums);
console.log("到達數組最后一個位置的最小跳躍次數:", minJumps);

代碼解釋

  1. 邊界條件處理:如果數組長度為 1,說明已經在最后一個位置,不需要跳躍,直接返回 0。
  2. 初始化變量
    • visited:一個布爾類型的數組,用于記錄每個位置是否已經被訪問過,初始時所有位置都標記為未訪問。
    • queue:一個隊列,用于存儲待擴展的位置和對應的跳躍次數,初始時將起始位置?0?和跳躍次數?0?加入隊列,并將起始位置標記為已訪問。
  3. BFS 過程
    • 當隊列不為空時,從隊列中取出一個元素,包含當前位置?currentIndex?和跳躍次數?jumps
    • 遍歷當前位置能跳躍到的所有位置?nextIndex(范圍是從?currentIndex + 1?到?currentIndex + nums[currentIndex]?且不超過數組長度)。
    • 如果?nextIndex?是最后一個位置,說明已經到達目標,返回當前跳躍次數加 1。
    • 如果?nextIndex?未被訪問過,將其標記為已訪問,并將?[nextIndex, jumps + 1]?加入隊列。
  4. 返回結果:如果一切正常,在 BFS 過程中會找到到達最后一個位置的最小跳躍次數并返回;理論上不會執行到返回?-1?的情況,因為題目保證可以到達最后一個位置。

復雜度分析

  • 時間復雜度:O(n),其中??是數組的長度。每個位置最多被訪問一次,因此時間復雜度為線性。
  • 空間復雜度:O(n),主要用于存儲?visited?數組和隊列,隊列在最壞情況下可能存儲所有位置。

與貪心算法相比,BFS 方法的代碼實現相對復雜一些,但它的思路更加直觀,適合用于解決一些需要搜索所有可能路徑的問題。不過,在這個特定問題中,貪心算法的時間和空間復雜度雖然與 BFS 相同,但在實際運行中可能會更快,因為貪心算法不需要維護隊列和訪問標記數組。

方法三:?動態規劃

動態規劃的核心思想是將原問題分解為子問題,通過求解子問題的最優解來得到原問題的最優解。

思路分析

  1. 定義狀態:設?dp[i]?表示到達數組中第?i?個位置所需的最小跳躍次數。
  2. 初始化狀態dp[0] = 0,因為初始位置就在?nums[0],不需要跳躍。對于其他位置?i,初始化為一個較大的值(比如?Infinity),表示暫時無法到達。
  3. 狀態轉移方程:對于每個位置?i,遍歷其前面的所有位置?j0 <= j < i),如果從位置?j?能夠跳到位置?i(即?j + nums[j] >= i),則更新?dp[i]?為?dp[j] + 1?和?dp[i]?中的較小值。
  4. 最終結果dp[n - 1]?即為到達數組最后一個位置所需的最小跳躍次數。

代碼實現

function jump(nums: number[]): number {const n = nums.length;// 初始化 dp 數組,dp[i] 表示到達第 i 個位置所需的最小跳躍次數const dp: number[] = new Array(n).fill(Infinity);// 初始位置不需要跳躍dp[0] = 0;// 遍歷數組中的每個位置for (let i = 1; i < n; i++) {// 遍歷 i 之前的所有位置for (let j = 0; j < i; j++) {// 如果從位置 j 能夠跳到位置 iif (j + nums[j] >= i) {// 更新 dp[i] 為 dp[j] + 1 和 dp[i] 中的較小值dp[i] = Math.min(dp[i], dp[j] + 1);}}}return dp[n - 1];
}// 示例調用
const nums = [2, 3, 1, 1, 4];
const minJumps = jump(nums);
console.log("到達數組最后一個位置的最小跳躍次數:", minJumps);

復雜度分析

  • 時間復雜度:O(n^2),其中??是數組的長度。因為需要使用兩層嵌套循環來填充?dp?數組。
  • 空間復雜度:O(n),主要用于存儲?dp?數組。

代碼解釋

  1. 初始化?dp?數組:創建一個長度為?n?的數組?dp,并將所有元素初始化為?Infinity,表示暫時無法到達。將?dp[0]?設為 0,因為初始位置不需要跳躍。
  2. 填充?dp?數組:使用兩層嵌套循環,外層循環遍歷從 1 到?n - 1?的每個位置?i,內層循環遍歷從 0 到?i - 1?的每個位置?j。對于每個位置?j,如果從位置?j?能夠跳到位置?i(即?j + nums[j] >= i),則更新?dp[i]?為?dp[j] + 1?和?dp[i]?中的較小值。
  3. 返回結果:最終返回?dp[n - 1],即到達數組最后一個位置所需的最小跳躍次數。

動態規劃方法雖然可以解決這個問題,但時間復雜度較高,在處理大規模數組時性能可能不如貪心算法。貪心算法的時間復雜度為?,是更優的解決方案。

?

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

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

相關文章

Qt的QToolBox的使用

QToolBox 是 Qt 框架中的一個控件&#xff0c;用于創建一個可折疊的“工具箱”界面&#xff08;類似 Windows 資源管理器的側邊欄&#xff09;。每個子項可以展開或折疊&#xff0c;適合用于分組顯示多個功能模塊。以下是其基本用法和示例&#xff1a; 1. 基本用法 創建并添加…

《DeepSeek 一站式工作生活 AI 助手》

最近國產AI工具DeepSeek在全球火出圈&#xff0c;登頂多個國家應用商店&#xff0c;下載量一路飆升。這匹AI “黑馬” 到底憑什么征服全球用戶&#xff1f;讓我們全方位解鎖DeepSeek——從基礎入門到高階玩法&#xff0c;從實用技巧到隱藏功能。 DeepSeek是一款功能強大的國產A…

Java中CompletableFuture異步工具類

參考&#xff1a;CompletableFuture 詳解 | JavaGuide 實際項目中&#xff0c;一個接口可能需要同時獲取多種不同的數據&#xff0c;然后再匯總返回&#xff0c;舉個例子&#xff1a;用戶請求獲取訂單信息&#xff0c;可能需要同時獲取用戶信息、商品詳情、物流信息、等數據。…

Oracle Rac 多路徑鏈路不穩定引發IO降速-光弱

一、背景 今天突然被異地的同事拉來開遠程會議&#xff0c;會議內容是開發反饋每天9點左右有個sqlldr 命令的腳本調用突然執行很慢&#xff0c;以前幾秒的導入操作現在需要30-60s左右&#xff0c;而且數據量基本相同。 二、分析 1&#xff09;、查看ASH報告 從報告上確認是數…

哈希表-兩個數的交集

代碼隨想錄-刷題筆記 349. 兩個數組的交集 - 力扣&#xff08;LeetCode&#xff09; 內容: 集合的使用 , 重復的數剔除掉&#xff0c;剩下的即為交集&#xff0c;最后加入數組即可。 class Solution {public int[] intersection(int[] nums1, int[] nums2) {Set<Integer…

[JVM篇]分代垃圾回收

分代垃圾回收 分代收集法是目前大部分 JVM 所采用的方法&#xff0c;其核心思想是根據對象存活的不同生命周期將內存劃分為不同的域&#xff0c;一般情況下將 GC 堆劃分為老生代(Tenured/Old Generation)和新生代(Young Generation)。老生代的特點是每次垃圾回收時只有少量對象…

漢諾塔問題詳解:遞歸與分治的經典案例

嘿&#xff0c;小伙伴們&#xff01;今天我可算撞見了個超有意思的東西&#xff0c;就是那大名鼎鼎的漢諾塔問題&#xff01;我這好奇心一下子就被勾起來了&#xff0c;迫不及待地想深挖一下&#xff0c;然后把那些好玩的、燒腦的、讓人拍案叫絕的解題思路和奇妙故事都分享給大…

vue中如何動態的增減組件的類名(class)

在 Vue.js 2 中&#xff0c;你可以通過計算屬性或直接在模板中使用 v-bind:class 來動態地改變組件的類名。下面是一個簡單的示例&#xff0c;說明如何在某個條件被復核后為組件添加一個 selected 類&#xff08;此處為組件添加一個默認的類&#xff08;例如 radio&#xff09;…

Vue3 基礎概念與環境搭建

一、Vue3 簡介 Vue3 是 Vue.js 的最新主要版本&#xff0c;于 2020 年 9 月正式發布。它在性能、可維護性和開發體驗方面都有了顯著的改進。相比 Vue2&#xff0c;Vue3 的主要特點包括&#xff1a; 更高效的響應式系統&#xff1a;使用 Proxy替代了 Object.defineProperty&…

華為昇騰920b服務器部署DeepSeek翻車現場

最近到禍一臺HUAWEI Kunpeng 920 5250&#xff0c;先看看配置。之前是部署的訊飛大模型&#xff0c;發現資源利用率太低了。把5臺減少到3臺&#xff0c;就出了他 硬件配置信息 基本硬件信息 按照慣例先來看看配置。一共3塊盤&#xff0c;500G的系統盤&#xff0c; 2塊3T固態…

Python的那些事第二十三篇:Express(Node.js)與 Python:一場跨語言的浪漫邂逅

摘要 在當今的編程世界里,Node.js 和 Python 像是兩個性格迥異的超級英雄,一個以速度和靈活性著稱,另一個則以強大和優雅聞名。本文將探討如何通過 Express 框架將 Node.js 和 Python 結合起來,打造出一個高效、有趣的 Web 應用。我們將通過一系列幽默風趣的實例和表格,展…

Word中接入大模型教程

前言 為什么要在word中接入大模型呢&#xff1f; 個人覺得最大的意義就是不用來回切換與復制粘貼了吧。 今天分享一下昨天實踐的在word中接入大模型的教程。 在word中接入大模型最簡單的方式就是使用vba。 vba代碼要做的事&#xff0c;拆分一下就是&#xff1a; 獲取用戶…

open3d繪制平面

在Open3D中繪制平面通常涉及到創建一個平面模型并將其可視化。Open3D是一個開源庫,主要用于3D數據的處理和可視化,但它主要用于3D數據的處理,并不直接支持繪制2D平面。如果你想在Open3D中“繪制”一個平面,你可以通過以下幾種方法來實現類似的效果: 方法1:使用o3d.geome…

DeepSeek R1 與 OpenAI O1:機器學習模型的巔峰對決

我的個人主頁 我的專欄&#xff1a;人工智能領域、java-數據結構、Javase、C語言&#xff0c;希望能幫助到大家&#xff01;&#xff01;&#xff01;點贊&#x1f44d;收藏? 一、引言 在機器學習的廣袤天地中&#xff0c;大型語言模型&#xff08;LLM&#xff09;無疑是最…

WebGPU頂點插槽進階優化指南:釋放GPU渲染性能

本文基于WebGPU官方規范與實踐經驗&#xff0c;深入探討頂點緩沖區的性能優化策略&#xff0c;涵蓋數據布局、資源管理、渲染流程等多個維度&#xff0c;并附詳細代碼注釋與性能對比分析。 一、數據布局優化&#xff1a;降低內存與帶寬壓力 1. 內存對齊策略 GPU對內存訪問有嚴…

數據結構實現順序表的尾插,尾刪,按值查找/修改/刪除,按下標查找/增加/刪除

頭文件&#xff1a;head.h #ifndef __HEAD_H__ #define __HEAD_H__#include <stdio.h> #include <string.h> #include <stdlib.h> #define MAXSIZE 20enum num {success,false-1};typedef int datatype;typedef struct {int len;datatype data[MAXSIZE]; }S…

基于Spring Boot+Vue的寵物服務管理系統(源碼+文檔)

項目簡介 寵物服務管理系統實現了以下功能&#xff1a; 基于Spring BootVue的寵物服務管理系統的主要使用者分為用戶管理模塊&#xff0c;由于系統運行在互聯網絡中&#xff0c;一些游客或者病毒惡意進行注冊&#xff0c;產生大量的垃圾用戶信息&#xff0c;管理員可以對這些…

2. grafana插件安裝并接入zabbix

一、在線安裝 如果不指定安裝位置&#xff0c;則默認安裝位置為/var/lib/grafana/plugins 插件安裝完成之后需要重啟grafana 命令在上一篇講到過 //查看相關幫助 [rootlocalhost ~]# grafana-cli plugins --help //從列舉中的插件過濾zabbix插件 [rootlocalhost ~]# grafana…

【Linux】Ubuntu Linux 系統——Python集成開發環境

??大家好&#xff0c;我是練小杰&#xff0c;今天周四了&#xff0c;明天就周五了&#xff0c;再堅持堅持又能休息了&#xff01;&#xff01;&#x1f606; 本文是有關Linux 操作系統中Python集成開發環境基礎知識&#xff0c;后續將添加更多相關知識噢&#xff0c;謝謝各位…

DeepSeek+即夢 做AI視頻

DeepSeek做AI視頻 制作流程第一步&#xff1a;DeepSeek 生成視頻腳本和分鏡 第二步&#xff1a;生成分鏡圖片繪畫提示詞第三步&#xff1a;生成分鏡圖片第四步&#xff1a;使用可靈 AI 工具&#xff0c;將生成的圖片轉成視頻。第五步&#xff1a;剪映成短視頻 DeepSeek 真的強&…