摘要:說明你可以假設數組中所有元素都是非負整數,且數值在位有符號整數范圍內。提示按奇偶排序數組給定一個非負整數數組,中一半整數是奇數,一半整數是偶數。對數組進行排序,以便當為奇數時,也是奇數當為偶數時,也是偶數。
原博客地址:https://finget.github.io/2019...排序
時間復雜度(運行次數)
我們假設計算機運行一行基礎代碼需要執行一次運算。
int aFunc(void) { printf("Hello, World! "); // 需要執行 1 次 return 0; // 需要執行 1 次 }
那么上面這個方法需要執行 2 次運算
int aFunc(int n) { for(int i = 0; i這個方法需要 (n + 1 + n + 1) = 2n + 2 次運算。
我們把 算法需要執行的運算次數 用 輸入大小n 的函數 表示,即 T(n) 。常用算法時間復雜度:
O(1)常數型
O(n)線性型
O(n^2)平方型
O(n^3)立方型
O(2^n)指數型
O(log2^n)對數型
O(nlog2^n)二維型
時間復雜度的分析方法:
1、時間復雜度就是函數中基本操作所執行的次數
2、一般默認的是最壞時間復雜度,即分析最壞情況下所能執行的次數
3、忽略掉常數項
4、關注運行時間的增長趨勢,關注函數式中增長最快的表達式,忽略系數
5、計算時間復雜度是估算隨著n的增長函數執行次數的增長趨勢
6、遞歸算法的時間復雜度為:遞歸總次數 * 每次遞歸中基本操作所執行的次數空間復雜度(占用內存)
算法消耗的空間
一個算法的占用空間是指算法實際占用的輔助空間總和
算法的空間復雜度
算法的空間復雜度不計算實際占用的空間,而是算整個算法的“輔助空間單元的個數”。算法的空間復雜度S(n)定義為該算法所耗費空間的數量級,它是問題規模n的函數。記作:S(n)=O(f(n)) 1若算法執行時所需要的輔助空間相對于輸入數據量n而言是一個常數,則稱這個算法的輔助空間為O(1);
冒泡排序
遞歸算法的空間復雜度:遞歸深度N*每次遞歸所要的輔助空間, 如果每次遞歸所需的輔助空間是常數,則遞歸的空間復雜度是 O(N).原理:從第一個元素開始,往后比較,遇到自己小的元素就交換位置let arr = [89, 19, 90, 9, 3, 21, 5, 77, 10, 22] function bubbleSort(arr) { for (let i = 0; i < arr.length; i++) { for (let j = 0; j < arr.length - 1 - i; j++) { if (arr[j] > arr[j + 1]) { [arr[j], arr[j + 1]] = [arr[j + 1], arr[j]] } } } return arr; } bubbleSort(arr)for (let j = 0; j < arr.length - 1 - i; j++)對于這里的理解:
當 i = 0 時, j的最大值是arr.length-2,那最后一個值就不比嗎?并不是,if (arr[j] > arr[j + 1])如果j
,j+1就會溢出。 那為什么又要-i呢,當i=0時,經過第一次循環,最大值就會放到數組的最后一位,此時,在進行第二次循環的時候i=1,最后的最大數就沒必要再比了,要比的就是前length-1-1項,以此類推,可以減少循環次數,控制時間復雜度,所以j < arr.length - 1 - i。
// 另一種寫法 let arr = [89, 19, 90, 9, 3, 21, 5, 77, 10, 22] function bubbleSort(arr) { // 用i來做邊界最大值 for (let i = arr.length - 1 ; i > 0 ; i--) { for (let j = 0; j < i; j++) { if (arr[j] > arr[j + 1]) { [arr[j], arr[j + 1]] = [arr[j + 1], arr[j]] } } } return arr; } bubbleSort(arr)選擇排序它的工作原理如下。首先在未排序序列中找到最小(大)元素,存放到排序序列的起始位置,然后,再從剩余未排序元素中繼續尋找最小(大)元素,然后放到已排序序列的末尾。以此類推,直到所有元素均排序完畢。let arr = [89, 19, 90, 9, 3, 21, 5, 77, 10, 22] function selectionSort(arr) { let len = arr.length; let min = ""; // 定一個最小值 // i < len-1 * 因為j = i + 1,不然會重復比較一次最后一位 for (let i = 0 ; i < len-1 ; i++) { min = i for (let j = i+1; j < len; j++) { if (arr[min] > arr[j]) { min = j } } [arr[i], arr[min]] = [arr[min], arr[i]] console.log(`i=${i}; min=${min}; arr=${arr}`) } return arr; } selectionSort(arr)// 循環過程 i=0; min=4; arr=3,19,90,9,89,21,5,77,10,22 i=1; min=6; arr=3,5,90,9,89,21,19,77,10,22 i=2; min=3; arr=3,5,9,90,89,21,19,77,10,22 i=3; min=8; arr=3,5,9,10,89,21,19,77,90,22 i=4; min=6; arr=3,5,9,10,19,21,89,77,90,22 i=5; min=5; arr=3,5,9,10,19,21,89,77,90,22 i=6; min=9; arr=3,5,9,10,19,21,22,77,90,89 i=7; min=7; arr=3,5,9,10,19,21,22,77,90,89 i=8; min=9; arr=3,5,9,10,19,21,22,77,89,90最大間距給定一個無序的數組,找出數組在排序之后,相鄰元素之間最大的差值。 如果數組元素個數小于 2,則返回 0。 示例?1: 輸入: [3,6,9,1] 輸出: 3 解釋: 排序后的數組是 [1,3,6,9], 其中相鄰元素 (3,6) 和 (6,9) 之間都存在最大差值 3。 示例?2: 輸入: [10] 輸出: 0 解釋: 數組元素個數小于 2,因此返回 0。 說明: 你可以假設數組中所有元素都是非負整數,且數值在 32 位有符號整數范圍內。 請嘗試在線性時間復雜度和空間復雜度的條件下解決此問題。var maximumGap = function(nums) { //if (nums.length < 2) { //return 0; // } //nums.sort((a,b) => a-b) //let max = 0; //for(let i = 0; i< nums.length-1; i++) { //max = nums[i+1]-nums[i]>max?nums[i+1]-nums[i]:max //} //return max; if (nums.length < 2) { return 0; } nums.sort((a,b) => a-b) let max = 0,grap; for(let i = 0; i< nums.length-1; i++) { grap = nums[i+1]-nums[i] max = grap>max?grap:max } return max; };// leetcode上的優解 /** * @param {number[]} nums * @return {number} */ var maximumGap = function (nums) { if (nums.length < 2) return 0 let max = nums[0], min = nums[0] for (let i = 1; i < nums.length; i++) { max = Math.max(nums[i], max) min = Math.min(nums[i], min) } let delta = (max - min) / (nums.length - 1) let maxBucket = new Array(nums.length - 1).fill(Number.MIN_SAFE_INTEGER) let minBucket = new Array(nums.length - 1).fill(Number.MAX_SAFE_INTEGER) for (let i = 0; i < nums.length; i++) { if (nums[i] == min || nums[i] == max) continue let index = Math.floor((nums[i] - min) / delta) maxBucket[index] = Math.max(maxBucket[index], nums[i]) minBucket[index] = Math.min(minBucket[index], nums[i]) } let prev = min, maxGap = 0 for (let i = 0; i < minBucket.length; i++) { if (minBucket[i] == Number.MAX_SAFE_INTEGER) continue maxGap = Math.max(minBucket[i] - prev, maxGap) prev = maxBucket[i] } maxGap = Math.max(max - prev, maxGap) return maxGap }; // 輸入 [3,6,9,1] // 最大值 9,最小值 1 // 最大桶 [-∞,-∞,-∞] 注意是反的,長度比原數組少1 // 最小桶 [+∞,+∞,+∞] 注意是反的,長度比原數組少1 // 平均桶間距 (9-1)/4 = 2 // 把值逐個放到桶 (nums[i]-最小值)/平均間距 // (3 - 1)/2 = 1 ,修改最小桶坐標1為3, [+∞,3,+∞],同理最大桶 [-∞,3,-∞] // (6 - 1)/2 = 2.5 = 2, 最小桶 [+∞,3,6] 最大桶 [-∞,3,6] // 9 為最大值,跳過 // 1 為最小值,跳過 // 如果有落在同一個桶的則最大桶取最大值,最小桶取最小值,此例子中沒有重復落入情況 // 從最小桶找到間隔最大的坐標 最小值=1,最小桶 [+∞,3,6],最大桶[-∞,3,6] 最大值=9 // 即較大間隔有3段,1-3(最小桶),3(最大桶)-6(最小桶),6(最大桶)-9 // 間隔 2,3,3 取最大 3按奇偶排序數組給定一個非負整數數組 A,返回一個數組,在該數組中,?A 的所有偶數元素之后跟著所有奇數元素。 你可以返回滿足此條件的任何數組作為答案。 ? 示例: 輸入:[3,1,2,4] 輸出:[2,4,3,1] 輸出 [4,2,3,1],[2,4,1,3] 和 [4,2,1,3] 也會被接受。 ? 提示: 1 <= A.length <= 5000 0 <= A[i] <= 5000var sortArrayByParity = function(A) { let arr = [] for(let i = 0;i按奇偶排序數組II 給定一個非負整數數組?A, A 中一半整數是奇數,一半整數是偶數。 對數組進行排序,以便當?A[i] 為奇數時,i?也是奇數;當?A[i]?為偶數時, i 也是偶數。 你可以返回任何滿足上述條件的數組作為答案。 示例: 輸入:[4,2,5,7] 輸出:[4,5,2,7] 解釋:[4,7,2,5],[2,5,4,7],[2,7,4,5] 也會被接受。 ? 提示: 2 <= A.length <= 20000 A.length % 2 == 0 0 <= A[i] <= 1000思路:利用雙指針,每次+2
var sortArrayByParityII = function(A) { let i = 0; let j = 1; while (j < A.length && i < A.length) { if (A[i] % 2 == 0) { i += 2; } else { while (A[j] % 2 != 0 && j < A.length) { j += 2; } if (j < A.length) { let tmp = A[i] A[i] = A[j] A[j] = tmp } } } return A; };缺失的第一個正數給定一個未排序的整數數組,找出其中沒有出現的最小的正整數。 示例?1: 輸入: [1,2,0] 輸出: 3 示例?2: 輸入: [3,4,-1,1] 輸出: 2 示例?3: 輸入: [7,8,9,11,12] 輸出: 1 說明: 你的算法的時間復雜度應為O(n),并且只能使用常數級別的空間。// 第一種解法 function firstMissingPositive(arr) { // 過濾到非正數 arr = arr.filter(item => item > 0); if(arr.length ==0) { // 數組為空說明沒有正數,那最小的正數就是1 return 1; } else { // 排序 arr.sort((a,b) => a-b); // 如果第一項不是1,那就返回1 if(arr[0] !== 1) { return 1 } else { for (let i = 0,len = arr.length; i < len; i++) { if(arr[i+1] - arr[i] > 1) { return arr[i] + 1 } } // 如果上面沒有return,那就返回數組最后一項 + 1 return arr.pop() + 1 } } };// 利用選擇排序優化代碼性能,上面那種寫法,最大的缺點就是對所有數據都進行了排序 function firstMissingPositive(arr) { arr = arr.filter(item => item > 0); // 選擇排序,先拿到最小值,如果第一個元素不是1就返回1 let min = 0; let len = arr.length; for (let i = 0; i < len; i++) { min = i; for (let j = i+1; j < len; j++) { if (arr[min] > arr[j]) { min = j } } [arr[i], arr[min]] = [arr[min], arr[i]] // 當進行到第二次遍歷后,就可以比較了 if (i>0) { if(arr[i]-arr[i-1]>1) { return arr[i-1] + 1 } } else { // 如果第一項最小正數不是1,就返回1 if (arr[0]!==1){ return 1; } } } // 上面的情況都沒通過,這也是最壞的情況,就判斷數組的長度如果為0就返回1,反之返回數組最后一項+1 return arr.length?arr.pop() + 1:1 }最后創建了一個前端學習交流群,感興趣的朋友,一起來嗨呀!
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://m.specialneedsforspecialkids.com/yun/104738.html
摘要:重復出現的子串要計算它們出現的次數。示例輸入輸出解釋有個子串,,,,它們具有相同數量的連續和。注意在到之間。以此類推,剃掉原字符串的第一個字符后再調用一次方法,直到原字符串只剩下個字符,返回數組的長度,即為題解。 博客原文地址:https://finget.github.io/2019... 反轉整數 給出一個 32 位的有符號整數,你需要將這個整數中每位上的數字進行反轉。 示例 ...
摘要:的最大公約數是,記為,,。示例輸入輸出示例輸入輸出注意數組內已種好的花不會違反種植規則。輸入的數組長度范圍為。是非負整數,且不會超過輸入數組的大小。 博客原文地址: https://finget.github.io/2019... 只出現一次的數字i 給定一個非空整數數組,除了某個元素只出現一次以外,其余每個元素均出現兩次。找出那個只出現了一次的元素。 說明: 你的算法應該具有線...
摘要:遍歷路徑,找到所有可以到達終點節點的路徑就是結果。提示中說保證輸入為有向無環圖,所以我們可以認為節點間一定有著某種排列的順序,從頭到尾怎樣可以有最多的路徑呢,那就是在保證沒有環路的情況下,所有節點都盡可能多的連接著其他節點。 ...
摘要:我們必須對數字數組進行升序排序,并找出給定數字在該數組中的位置。算法說明將值第二個參數插入到數組第一個參數中,并返回其在排序后的數組中的最低索引。我們的目標是將輸入的數字在輸入數組后中排序后,再返回它的索引。 翻譯:瘋狂的技術宅原文:https://medium.freecodecamp.o... 本文首發微信公眾號:前端先鋒歡迎關注,每天都給你推送新鮮的前端技術文章 編寫算法時...
文章目錄 一、題目1、題目描述2、基礎框架3、原題鏈接 二、解題報告1、思路分析2、時間復雜度3、代碼詳解 三、本題小知識四、加群須知 一、題目 1、題目描述 ??給你一棵二叉搜索樹,請按 中序遍歷 將其重新排列為一棵遞增順序搜索樹,使樹中最左邊的節點成為樹的根節點,并且每個節點沒有左子節點,只有一個右子節點。??樣例輸入: [5,3,6,2,4,null,8,1,null,null,nu...
閱讀 907·2021-10-13 09:39
閱讀 1494·2021-10-11 10:57
閱讀 2605·2019-08-26 13:53
閱讀 2550·2019-08-26 12:23
閱讀 3700·2019-08-23 18:30
閱讀 3759·2019-08-23 18:08
閱讀 2535·2019-08-23 18:04
閱讀 2968·2019-08-23 16:28