【力扣 Hot100】刷題日記

D8 全排列(非回溯法)

全排列原題鏈接

在刷leetcode的時候,看到這道題目并沒法使用像STL的next_permutation方法,感嘆C++便利的同時,又惋惜Java并沒有類似的API,那我們只能從原理入手了,仿寫此算法。

其實回溯法更應該掌握,因為擴展性高,我們學知識本來就是舉一反三的,如果這個算法只適用于這道題,那我們深入學習的必要性就沒那么大了。

我們來看實現過程:

1. 找到「下降點」i

  • 從右向左掃描數組,找到第一個 arr[i] < arr[i+1] 的位置 i
  • 為什么要找這個?因為字典序的排列從右向左最長的非遞增序列是當前排列的尾部,我們想找到可以“升高”的那個位置。

說人話就是,這里非遞增序列我們先理解為遞減序列(其實還包括前后相等),其實是找遞減序列的入口,為什么呢?

因為按照字典序來看,這一部分是不便于排列的,因為難以升高,我們得優先換這部分的前一部分。

如果還是不理解,可以繼續往后看,看到后面就會明白這里為什么找下降點。

舉例:
arr = [1, 3, 5, 4, 2]
從右往左,觀察 arr[i] >= arr[i+1]

  • 4 >= 2 → 是
  • 5 >= 4 → 是
  • 3 >= 5 → 否,3 < 5
    所以 i = 1(對應數字 3)。
  • 如果 i < 0,說明整個數組是非遞增序列(即當前排列是最大字典序),沒有下一個排列,函數返回 false

2. 找到交換點 j

  • 從右向左找到第一個 arr[j] > arr[i] 的位置。
  • arr[i] 后面的序列中找一個比 arr[i] 大的最小數字交換,使排列字典序剛好變大一點。

繼續上例:
i=1arr[i]=3
從右往左找第一個比 3 大的元素:

  • 2 <= 3 不符合
  • 4 > 3 符合,且是最右邊的符合條件元素
    所以 j = 3

3. 交換 arr[i]arr[j]

交換 34,變成:

[1, 4, 5, 3, 2]

4. 反轉 i+1 位置到數組末尾的部分

i+1 到末尾的子數組反轉(升序排列),保證新排列是字典序中「緊接著」的下一排列。

這里 i+1=2,子數組是 [5, 3, 2],反轉后是 [2, 3, 5],數組變成:

[1, 4, 2, 3, 5]

這個就是字典序的下一個排列。

既然這樣,那么我們需要實現兩個函數swapreverse

class Solution {public List<List<Integer>> permute(int[] nums) {Arrays.sort(nums); //這段代碼用于判斷List<List<Integer>> ans = new ArrayList<>();do{List<Integer> temp = new ArrayList<>();for (int num : nums) {temp.add(num);}ans.add(temp);}while(nextPermutation(nums));return ans;}private static boolean nextPermutation(int[] arr){int i = arr.length - 2;while(i >= 0 && arr[i] >= arr[i + 1]) i--; //找到下降點if(i < 0) return false;int j = arr.length - 1;while(arr[j] <= arr[i]) j--; //找出比下降點大的swap(arr, i, j);reverse(arr, i + 1, arr.length - 1);return true;}private static void swap(int[] arr, int i, int j){int temp = arr[i];arr[i] = arr[j];arr[j] = temp;}private static void reverse(int arr[], int l, int r){while(l < r) swap(arr, l++, r--);}
}

如果這篇文章對你有幫助,請點贊評論收藏,創作不易,你的支持是我堅持的動力。

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

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

相關文章

JetPack系列教程(七):Palette——讓你的APP色彩“飛”起來!

JetPack系列教程&#xff08;七&#xff09;&#xff1a;Palette——讓你的APP色彩“飛”起來&#xff01; 各位開發小伙伴們&#xff0c;還在為APP的配色發愁嗎&#xff1f;別擔心&#xff0c;今天咱們就來聊聊JetPack家族里的“色彩魔法師”——Palette&#xff01;這個神奇的…

力扣hot100 | 矩陣 | 73. 矩陣置零、54. 螺旋矩陣、48. 旋轉圖像、240. 搜索二維矩陣 II

73. 矩陣置零 力扣題目鏈接 給定一個 m x n 的矩陣&#xff0c;如果一個元素為 0 &#xff0c;則將其所在行和列的所有元素都設為 0 。請使用 原地 算法。 示例 1&#xff1a; 輸入&#xff1a;matrix [[1,1,1],[1,0,1],[1,1,1]] 輸出&#xff1a;[[1,0,1],[0,0,0],[1,0,1]]…

ARC與eARC是什么?主要用在哪?

在家庭影音設備不斷升級的今天&#xff0c;人們對音視頻體驗的要求越來越高。無論是追劇、玩游戲還是觀看電影大片&#xff0c;很多用戶不再滿足于電視自帶的揚聲器&#xff0c;而是希望借助回音壁、功放或家庭影院系統&#xff0c;獲得更加震撼的沉浸式聲音體驗。一、ARC是什么…

解鎖JavaScript性能優化:從理論到實戰

文章目錄 前言 一、常見性能瓶頸剖析 二、實戰案例與優化方案 (一)DOM 操作優化案例? (二)事件綁定優化案例? (三)循環與遞歸優化案例? (四)內存管理優化案例? 三、性能優化工具介紹 總結 前言 性能優化的重要性 在當今數字化時代,Web 應用已成為人們生活和工作…

結構化記憶、知識圖譜與動態遺忘機制在醫療AI中的應用探析(上)

往期相關內容推薦: 基于Python的多元醫療知識圖譜構建與應用研究(上)

XSS攻擊:從原理入門到實戰精通詳解

一、XSS攻擊基礎概念1.1 什么是XSS攻擊 XSS&#xff08;Cross-Site Scripting&#xff0c;跨站腳本攻擊&#xff09;是一種將惡意腳本注入到可信網站中的攻擊手段。當用戶訪問被注入惡意代碼的頁面時&#xff0c;瀏覽器會執行這些代碼&#xff0c;導致&#xff1a;用戶會話被劫…

Leetcode 14 java

今天復習一下以前做過的題目&#xff0c;感覺是忘光了。 160. 相交鏈表 給你兩個單鏈表的頭節點 headA 和 headB &#xff0c;請你找出并返回兩個單鏈表相交的起始節點。如果兩個鏈表不存在相交節點&#xff0c;返回 null 。 圖示兩個鏈表在節點 c1 開始相交&#xff1a; 題目數…

用 FreeMarker 動態構造 SQL 實現數據透視分析

在 ERP、BI 等系統中&#xff0c;數據透視分析&#xff08;Pivot Analysis&#xff09;是非常常見的需求&#xff1a;用戶希望按任意維度&#xff08;如門店、時間、商品分類等&#xff09;進行分組統計&#xff0c;同時選擇不同的指標&#xff08;如 GMV、訂單數、客單價等&am…

13.深度學習——Minst手寫數字識別

第一部分——起手式 import torch from torchvision import datasets, transforms import torch.nn as nn import torch.nn.functional as F import torch.optim as optimuse_cuda torch.cuda.is_available()if use_cuda:device torch.device("cuda") else: device…

【JAVA高級】實現word轉pdf 實現,源碼概述。深坑總結

之前的需求做好后,需求,客戶突發奇想。要將生成的word轉為pdf! 因為不想讓下載文檔的人改動文檔。 【JAVA】實現word添加標簽實現系統自動填入字段-CSDN博客 事實上這個需求難度較高,并不是直接轉換就行的 word文檔當中的很多東西都需要處理 public static byte[] gener…

數據驅動測試提升自動化效率

測試工程師老王盯著滿屏重復代碼嘆氣&#xff1a;“改個搜索條件要重寫20個腳本&#xff0c;這班加到啥時候是個頭&#xff1f;” 隔壁組的小李探過頭&#xff1a;“試試數據驅動唄&#xff0c;一套腳本吃遍所有數據&#xff0c;我們組上周測了300個組合都沒加班&#xff01;”…

模板引用(Template Refs)全解析2

三、v-for 中的模板引用 當在 v-for 中使用模板引用時,引用的 value 會自動變為一個數組,包含列表中所有元素/組件的引用(需 Vue 3.5+ 版本,舊版需手動處理且順序不保證)。 1. 基本用法(Vue 3.5+) <script setup> import { ref, useTemplateRef, onMounted } f…

【Linux系統】進程間通信:System V IPC——共享內存

前文中我們介紹了管道——匿名管道和命名管道來實現進程間通信&#xff0c;在介紹怎么進行通信時&#xff0c;我們有提到過不止管道的方式進行通信&#xff0c;還有System V IPC&#xff0c;今天這篇文章我們就來學習一下System V IPC中的共享內存1. 為何引入共享內存&#xff…

[優選算法專題二滑動窗口——最大連續1的個數 III]

題目鏈接 最大連續1的個數 III 題目描述 題目解析 問題本質 輸入&#xff1a;二進制數組nums&#xff08;只包含 0 和 1&#xff09;和整數k操作&#xff1a;最多可以將k個 0 翻轉成 1目標&#xff1a;找到翻轉后能得到的最長連續 1 的子數組長度 這個問題的核心是要找到一…

C#單元測試(xUnit + Moq + coverlet.collector)

C#單元測試 xUnit Moq coverlet.collector 1.添加庫 MlyMathLib 2.編寫庫函數內容 using System;namespace MlyMathLib {public interface IUserRepo{string GetName(int id);}public class UserService{private readonly IUserRepo _repo;public UserService(IUserRepo repo…

【數據庫】Oracle學習筆記整理之五:ORACLE體系結構 - 參數文件與控制文件(Parameter Files Control Files)

Oracle體系結構 - 參數文件與控制文件&#xff08;Parameter Files & Control Files&#xff09; 參數文件與控制文件是Oracle數據庫的“雙核基石”&#xff1a;參數文件是實例的“啟動配置中心”&#xff0c;定義運行環境與規則&#xff1b;控制文件是數據庫的“物理元數據…

GDB典型開發場景深度解析

GDB典型開發場景深度解析 以下是開發過程中最常見的GDB使用場景&#xff0c;結合具體實例和調試技巧&#xff0c;幫助開發者高效解決實際問題&#xff1a;一、崩潰分析&#xff08;Core Dump調試&#xff09; 場景&#xff1a;程序突然崩潰&#xff0c;生成了core文件 # 啟動調…

存儲、硬盤、文件系統、 IO相關常識總結

目錄 &#xff08;一&#xff09;存儲 &#xff08;1&#xff09;定義 &#xff08;2&#xff09;分類 &#xff08;二&#xff09;硬盤 &#xff08;1&#xff09;容量&#xff08;最主要的參數&#xff09; &#xff08;2&#xff09;轉速 &#xff08;3&#xff09;訪…

docker安裝mongodb及java連接實戰

1.docker部署mongodb docker run --name mongodb -d -p 27017:27017 -v /data/mongodbdata:/data/db -e MONGO_INITDB_ROOT_USERNAMEtestmongo -e MONGO_INITDB_ROOT_PASSWORDtest123456 mongodb:4.0.112.項目實戰 <dependencies><dependency><groupId>org.m…

Java設計模式之《工廠模式》

目錄 1、介紹 1.1、定義 1.2、優缺點 1.3、使用場景 2、實現 2.1、簡單工廠模式 2.2、工廠方法模式 2.3、抽象工廠模式 3、小結 前言 在面向對象編程中&#xff0c;創建對象實例最常用的方式就是通過 new 操作符構造一個對象實例&#xff0c;但在某些情況下&#xff0…