【動態規劃】二分優化最長上升子序列

最長上升子序列 II 題解

題目傳送門:AcWing 896. 最長上升子序列 II

一、題目描述

給定一個長度為 N 的數列,求數值嚴格單調遞增的子序列的長度最長是多少。

輸入格式

  • 第一行包含整數 N
  • 第二行包含 N 個整數,表示完整序列

輸出格式

  • 輸出一個整數,表示最大長度

數據范圍

  • 1 ≤ N ≤ 100000
  • -10? ≤ 數列中的數 ≤ 10?

二、題目分析

這道題要求我們找到一個序列中最長的嚴格遞增子序列的長度。與普通的最長上升子序列問題不同,本題的數據范圍較大(N ≤ 1e5),因此需要使用優化的算法。

三、解題思路

傳統的動態規劃解法時間復雜度為O(n2),對于n=1e5的情況會超時。我們需要使用貪心+二分的方法將時間復雜度優化到O(nlogn)。

基本思路是維護一個數組a,其中a[i]表示長度為i+1的上升子序列的最小末尾元素。對于每個元素,我們使用二分查找來確定它應該插入的位置,從而保持數組a的單調性。

四、算法講解

算法原理

  1. 貪心思想:我們希望上升子序列盡可能長,因此需要讓序列上升得盡可能慢,即每次在上升子序列最后加上的數盡可能小。
  2. 單調性:數組a是一個嚴格遞增的數組,這保證了我們可以使用二分查找。
  3. 二分查找:對于每個新元素,如果它大于數組a的最后一個元素,則直接添加到末尾;否則,使用二分查找找到第一個大于等于它的位置并替換。

算法實現步驟

  1. 初始化空數組a和計數器cnt=0
  2. 遍歷輸入序列中的每個元素x
    • 如果x大于a的最后一個元素,直接添加到a末尾,cnt加1
    • 否則,使用二分查找找到a中第一個大于等于x的位置,并用x替換該位置的值
  3. 最終cnt即為最長上升子序列的長度

例子講解

以輸入樣例為例:

7
3 1 2 1 8 5 6

處理過程:

  1. 3 → [3], cnt=1
  2. 1 → [1], cnt=1 (替換3)
  3. 2 → [1,2], cnt=2
  4. 1 → [1,2], cnt=2 (1替換1,無變化)
  5. 8 → [1,2,8], cnt=3
  6. 5 → [1,2,5], cnt=3 (替換8)
  7. 6 → [1,2,5,6], cnt=4

最終結果為4。

五、代碼實現

#include <bits/stdc++.h>
using namespace std;
// #define int long long
const int N = 1e5 + 10;
int n;
int a[N];
int cnt = 0, f[N];// STL大法
void solve1()
{cin >> n;for (int i = 1; i <= n; i ++){int x;cin >> x;if (cnt == 0 || a[cnt - 1] < x)a[cnt++] = x;else*lower_bound(a, a + cnt, x) = x; // 使用STL的lower_bound找到第一個≥x的位置并替換}cout << cnt;
}// 手寫二分
void solve2()
{cin >> n;for (int i = 1; i <= n; i ++){int x;cin >> x;if (cnt == 0 || a[cnt - 1] < x)a[cnt++] = x;else{int l = -1, r = cnt + 1;while (l + 1 != r) // 二分查找第一個≥x的位置{int mid = l + r >> 1;if (a[mid] < x)l = mid;else r = mid;}a[r] = x; // 替換該位置的值}}cout << cnt;
}signed main()
{ios::sync_with_stdio(false), cin.tie(0), cout.tie(0);// solve1();solve2();return 0;
}

六、重點細節

  1. 初始化邊界:二分查找時,左邊界設為-1,右邊界設為cnt+1,這樣可以處理所有可能的情況
  2. 嚴格遞增:題目要求嚴格遞增,因此比較時使用<而不是≤
  3. 替換策略:當找到第一個≥x的位置時,直接替換可以保證后續更長的子序列更容易形成
  4. 數組維護:數組a的長度cnt即為當前找到的最長上升子序列長度

七、復雜度分析

  • 時間復雜度:O(nlogn),每個元素需要進行一次二分查找,二分查找的時間復雜度為O(logn)
  • 空間復雜度:O(n),需要額外的數組a來存儲中間結果

八、總結

本題通過貪心+二分的方法,將最長上升子序列問題的時間復雜度從O(n2)優化到O(nlogn),能夠高效處理大規模數據。關鍵在于維護一個單調遞增的數組,并通過二分查找來快速確定每個元素的插入位置。

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

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

相關文章

Dify接口api對接,流式接收流式返回(.net)

試了好多種方法除了Console.WriteLine()能打印出來&#xff0c;試了好些方法都不行&#xff0c;不是報錯就是打印只有一行&#xff0c;要么就是接收完才返回...下面代碼實現調用api接收流式數據&#xff0c;并進行流式返回給前端&#xff1a; using Furion.HttpRemote; using …

19-元素顯示模式及浮動(CSS3)

知識目標 掌握標準文檔流的解析規則掌握元素的顯示模式掌握元素浮動屬性語法與使用掌握浮動塌陷解決方法 1. 標準文檔流 2. 元素顯示模式 元素顯示模式就是元素&#xff08;標簽&#xff09;以什么方式進行顯示&#xff0c;比如<div>獨占一行&#xff0c;一行可以放多…

HTML jQuery 項目 PDF 批注插件庫在線版 API 示例教程

本文章介紹 HTML && jQuery Web項目中 PDF 批注插件庫 ElasticPDF 在線版 API 示例教程&#xff0c;API 包含 ① 導出批注后PDF數據&#xff1b;② 導出純批注 json 數據&#xff1b;③ 加載舊批注&#xff1b;④ 切換文檔&#xff1b;⑤ 切換用戶&#xff1b;⑥ 清空批…

CATIA裝配體全自動存儲解決方案開發實戰——基于遞歸算法的產品結構樹批量處理技術

一、功能定位與技術架構 本工具針對CATIA V5裝配體文件管理場景&#xff0c;實現了一套全自動遞歸存儲系統&#xff0c;主要功能包括&#xff1a; ?智能路徑選擇&#xff1a;通過Tkinter目錄對話框實現可視化路徑選擇?產品結構遞歸解析&#xff1a;深度優先遍歷裝配體中的子…

C#:接口(interface)

目錄 接口的核心是什么&#xff1f; 1. 什么是接口&#xff08;Interface&#xff09;&#xff0c;為什么要用它&#xff1f; 2. 如何定義和使用接口&#xff1f; 3.什么是引用接口&#xff1f; 如何“引用接口”&#xff1f; “引用接口”的關鍵點 4. 接口與抽象類的區…

基于卷積神經網絡CNN實現電力負荷多變量時序預測(PyTorch版)

前言 系列專欄:【深度學習:算法項目實戰】?? 涉及醫療健康、財經金融、商業零售、食品飲料、運動健身、交通運輸、環境科學、社交媒體以及文本和圖像處理等諸多領域,討論了各種復雜的深度神經網絡思想,如卷積神經網絡、循環神經網絡、生成對抗網絡、門控循環單元、長短期記…

關于inode,dentry結合軟鏈接及硬鏈接的實驗

一、背景 在之前的博客 缺頁異常導致的iowait打印出相關文件的絕對路徑-CSDN博客 里 2.2.3 一節里&#xff0c;我們講到了file&#xff0c;fd&#xff0c;inode&#xff0c;dentry&#xff0c;super_block這幾個概念&#xff0c;在這篇博客里&#xff0c;我們針對inode和dentr…

游戲引擎學習第201天

倉庫:https://gitee.com/mrxiao_com/2d_game_5 回顧之前的內容&#xff0c;并遇到了一次一階異常&#xff08;First-Chance Exception&#xff09;。 歡迎來到新一期的開發過程&#xff0c;我們目前正在編寫調試接口代碼。 當前&#xff0c;我們已經在布局系統上進行了一些工…

計算機視覺算法實戰——基于YOLOv8的行人流量統計系統

?個人主頁歡迎您的訪問 ?期待您的三連 ? ?個人主頁歡迎您的訪問 ?期待您的三連 ? ?個人主頁歡迎您的訪問 ?期待您的三連? ??? ????????? ?? 引言:智能客流分析的市場需求 在零售、交通、安防等領域,準確的行人流量統計對于商業決策、公共安全管理…

Redis是什么?架構是怎么樣的?

目錄 前言 一,Redis架構 1.1 本地緩存 1.2 遠程緩存 二,強大的Redis優點 2.1 支持多種數據類型 2.2 內存過期策略 2.3 內存淘汰策略 2.4 持久化 三,Redis是什么 前言 我是一個程序員,維護了一個商品服務,它的背后直連Mysql數據庫,假設商品服務對外每秒需要提供1萬次…

藍橋杯真題——傳送陣

原題連接&#xff1a;藍橋杯2024年第十五屆省賽真題-傳送陣 - C語言網 知識點&#xff1a;并查集 題目描述 小藍在環球旅行時來到了一座古代遺跡&#xff0c;里面并排放置了 n 個傳送陣&#xff0c;進入第 i 個傳送陣會被傳送到第 ai 個傳送陣前&#xff0c;并且可以隨時選擇…

彩虹表攻擊

1. 引言 密碼安全一直是信息安全領域的重要課題。攻擊者可以利用**暴力破解(Brute-Force Attack)和字典攻擊(Dictionary Attack)等方式嘗試破解密碼。然而,計算機性能的提升使得這些方法的效率不斷提高,其中彩虹表攻擊(Rainbow Table Attack)**是一種極具威脅性的密碼…

Vue2 監聽器 watcher

文章目錄 前言監聽器的作用&#xff1a;工作流程&#xff1a;基本用法1. 簡單監聽2. 對象形式配置 使用場景1. 執行異步操作2. 監聽路由變化3. 復雜對象/數組變化 關鍵配置項與計算屬性的區別動態添加監聽器注意事項 前言 提示&#xff1a;這里可以添加本文要記錄的大概內容&a…

Linux系統程序設計:從入門到高級Day02

這一篇 我帶大家復習一下&#xff0c;C語言中的文件 那一部分 大家注意 這里的圖并非原創 是當時我老師的圖片 本片作用主要是 后續會有文件相關操作&#xff0c;這篇幫大家復習C語言文件中的內容 有助于大家后面的理解。 文章中代碼大多是圖片格式&#xff0c;是因為這是我…

N元語言模型的時間和空間復雜度計算

對于N元語言模型&#xff0c;時間復雜度是O(V ^ {N-1})&#xff0c;空間復雜度是O(V ^ {N})&#xff0c;N是詞匯表的大小。 空間復雜度&#xff1a;存儲所有可能的N-1元組及其對應的詞的頻次需要大量的存儲空間。例如&#xff0c;對于一個三元模型&#xff08;N3&#xff09;&…

Tmux 核心操作速查指南

Tmux 最常用操作筆記 1. 基本概念 會話&#xff08;Session&#xff09;&#xff1a;一個tmux會話可以包含多個窗口&#xff0c;適合長期任務管理。窗口&#xff08;Window&#xff09;&#xff1a;每個窗口是一個獨立的終端界面&#xff0c;可包含多個面板。面板&#xff08…

哈希表系列一>兩數之和

目錄 題目&#xff1a;方法&#xff1a;暴力代碼&#xff1a;優化后代碼&#xff1a; 題目&#xff1a; 鏈接: link 方法&#xff1a; 暴力代碼&#xff1a; public int[] twoSum(int[] nums, int target) {解法一&#xff1a;暴力解法&#xff1a;int n nums.length;for(int…

端到端機器學習流水線(MLflow跟蹤實驗)

目錄 端到端機器學習流水線(MLflow跟蹤實驗)1. 引言2. 項目背景與意義2.1 端到端機器學習流水線的重要性2.2 MLflow的作用2.3 工業級數據處理需求3. 數據集生成與介紹3.1 數據集構成3.2 數據生成方法4. 機器學習流水線與MLflow跟蹤4.1 端到端機器學習流水線4.2 MLflow跟蹤實驗…

英語學習:讀科技論文的難處

如果讀起科技論文&#xff0c; 我們就知道自己到底欠缺什么知識了&#xff0c; 那是一個挨著一個的缺。 而且還沒有維基百科可用。 怎么辦&#xff1f;沒辦法&#xff01;硬看&#xff01; 而且還要面臨語言的差異性困難。比如這一句怎么翻譯比較合適&#xff1f;還是直接不翻譯…

001 使用單片機實現的邏輯分析儀——吸收篇

本內容記錄于韋東山老師的畢設級開源學習項目&#xff0c;含個人觀點&#xff0c;請理性閱讀。 個人筆記&#xff0c;沒有套路&#xff0c;一步到位&#xff0c;歡迎交流&#xff01; 00單片機的邏輯分析儀與商業版FPGA的邏輯分析儀異同 對比維度自制STM32邏輯分析儀商業版邏…