日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

[Leedcode][JAVA][第4题][寻找两个正序数组中的中位数][二分查找][双指针]

發布時間:2023/12/10 编程问答 28 豆豆
生活随笔 收集整理的這篇文章主要介紹了 [Leedcode][JAVA][第4题][寻找两个正序数组中的中位数][二分查找][双指针] 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

【問題描述】[困難]

給定兩個大小為 m 和 n 的正序(從小到大)數組 nums1 和 nums2。請你找出這兩個正序數組的中位數,并且要求算法的時間復雜度為 O(log(m + n))。你可以假設 nums1 和 nums2 不會同時為空。示例 1:nums1 = [1, 3] nums2 = [2]則中位數是 2.0 示例 2:nums1 = [1, 2] nums2 = [3, 4]來源:力扣(LeetCode) 鏈接:https://leetcode-cn.com/problems/median-of-two-sorted-arrays 著作權歸領扣網絡所有。商業轉載請聯系官方授權,非商業轉載請注明出處。

【解答思路】

1. 數組合并

兩個數組合并,兩個有序數組的合并也是歸并排序中的一部分。然后根據奇數,還是偶數,返回中位數
時間復雜度:O(N+M) 空間復雜度:O(1)

public double findMedianSortedArrays(int[] nums1, int[] nums2) {int[] nums;int m = nums1.length;int n = nums2.length;nums = new int[m + n];if (m == 0) {if (n % 2 == 0) {return (nums2[n / 2 - 1] + nums2[n / 2]) / 2.0;} else {return nums2[n / 2];}}if (n == 0) {if (m % 2 == 0) {return (nums1[m / 2 - 1] + nums1[m / 2]) / 2.0;} else {return nums1[m / 2];}}int count = 0;int i = 0, j = 0;while (count != (m + n)) {if (i == m) {while (j != n) {nums[count++] = nums2[j++];}break;}if (j == n) {while (i != m) {nums[count++] = nums1[i++];}break;}if (nums1[i] < nums2[j]) {nums[count++] = nums1[i++];} else {nums[count++] = nums2[j++];}}if (count % 2 == 0) {return (nums[count / 2 - 1] + nums[count / 2]) / 2.0;} else {return nums[count / 2];} }
2. 雙指針


時間復雜度:O(N+M) 空間復雜度:O(1)

public double findMedianSortedArrays(int[] A, int[] B) {int m = A.length;int n = B.length;int len = m + n;int left = -1, right = -1;int aStart = 0, bStart = 0;for (int i = 0; i <= len / 2; i++) {left = right;if (aStart < m && (bStart >= n || A[aStart] < B[bStart])) {right = A[aStart++];} else {right = B[bStart++];}}if ((len & 1) == 0)return (left + right) / 2.0;elsereturn right; }
3. 求第 k 小數 k/2





時間復雜度:O(log(m+n) 空間復雜度:O(1)

public double findMedianSortedArrays(int[] nums1, int[] nums2) {int n = nums1.length;int m = nums2.length;int left = (n + m + 1) / 2;int right = (n + m + 2) / 2;//將偶數和奇數的情況合并,如果是奇數,會求兩次同樣的 k 。return (getKth(nums1, 0, n - 1, nums2, 0, m - 1, left) + getKth(nums1, 0, n - 1, nums2, 0, m - 1, right)) * 0.5; }private int getKth(int[] nums1, int start1, int end1, int[] nums2, int start2, int end2, int k) {int len1 = end1 - start1 + 1;int len2 = end2 - start2 + 1;//讓 len1 的長度小于 len2,這樣就能保證如果有數組空了,一定是 len1 if (len1 > len2) return getKth(nums2, start2, end2, nums1, start1, end1, k);if (len1 == 0) return nums2[start2 + k - 1];if (k == 1) return Math.min(nums1[start1], nums2[start2]);int i = start1 + Math.min(len1, k / 2) - 1;int j = start2 + Math.min(len2, k / 2) - 1;if (nums1[i] > nums2[j]) {return getKth(nums1, start1, end1, nums2, j + 1, end2, k - (j - start2 + 1));}else {return getKth(nums1, i + 1, end1, nums2, start2, end2, k - (i - start1 + 1));}}
4. 中位數







用完

長度相等


時間復雜度:O(N) 空間復雜度:O(1)

class Solution {public double findMedianSortedArrays(int[] nums1, int[] nums2) {int leftLength = nums1.length;int rightLength = nums2.length;// 為了保證第一個數組比第二個數組小(或者相等)if (leftLength > rightLength) {return findMedianSortedArrays(nums2, nums1);}// 分割線左邊的所有元素需要滿足的個數 m + (n - m + 1) / 2;// 兩個數組長度之和為偶數時,當在長度之和上+1時,由于整除是向下取整,所以不會改變結果// 兩個數組長度之和為奇數時,按照分割線的左邊比右邊多一個元素的要求,此時在長度之和上+1,就會被2整除,會在原來的數//的基礎上+1,于是多出來的那個1就是左邊比右邊多出來的一個元素int totalLeft = (leftLength + rightLength + 1) / 2;// 在 nums1 的區間 [0, leftLength] 里查找恰當的分割線,// 使得 nums1[i - 1] <= nums2[j] && nums2[j - 1] <= nums1[i]int left = 0;int right = leftLength;// nums1[i - 1] <= nums2[j]// 此處要求第一個數組中分割線的左邊的值 不大于(小于等于) 第二個數組中分割線的右邊的值// nums2[j - 1] <= nums1[i]// 此處要求第二個數組中分割線的左邊的值 不大于(小于等于) 第一個數組中分割線的右邊的值// 循環條件結束的條件為指針重合,即分割線已找到while (left < right) {// 二分查找,此處為取第一個數組中左右指針下標的中位數,決定起始位置// 此處+1首先是為了不出現死循環,即left永遠小于right的情況// left和right最小差距是1,此時下面的計算結果如果不加1會出現i一直=left的情況,而+1之后i才會=right// 于是在left=i的時候可以破壞循環條件,其次下標+1還會保證下標不會越界,因為+1之后向上取整,保證了// i不會取到0值,即i-1不會小于0// 此時i也代表著在一個數組中左邊的元素的個數//+1 防止死循環int i = left + (right - left + 1) / 2;// 第一個數組中左邊的元素個數確定后,用左邊元素的總和-第一個數組中元素的總和=第二個元素中左邊的元素的總和// 此時j就是第二個元素中左邊的元素的個數int j = totalLeft - i;// 此處用了nums1[i - 1] <= nums2[j]的取反,當第一個數組中分割線的左邊的值大于第二個數組中分割線的右邊的值// 說明又指針應該左移,即-1if (nums1[i - 1] > nums2[j]) {// 下一輪搜索的區間 [left, i - 1]right = i - 1;// 此時說明條件滿足,應當將左指針右移到i的位置,至于為什么是右移,請看i的定義} else {// 下一輪搜索的區間 [i, right]left = i;}}// 退出循環時left一定等于right,所以此時等于left和right都可以// 為什么left一定不會大于right?因為left=i。// 此時i代表分割線在第一個數組中所在的位置// nums1[i]為第一個數組中分割線右邊的第一個值// nums[i-1]即第一個數組中分割線左邊的第一個值int i = left;// 此時j代表分割線在第二個數組中的位置// nums2[j]為第一個數組中分割線右邊的第一個值// nums2[j-1]即第一個數組中分割線左邊的第一個值int j = totalLeft - i;// 當i=0時,說明第一個數組分割線左邊沒有值,為了不影響// nums1[i - 1] <= nums2[j] 和 Math.max(nums1LeftMax, nums2LeftMax)// 的判斷,所以將它設置為int的最小值int nums1LeftMax = i == 0 ? Integer.MIN_VALUE : nums1[i - 1];// 等i=第一個數組的長度時,說明第一個數組分割線右邊沒有值,為了不影響// nums2[j - 1] <= nums1[i] 和 Math.min(nums1RightMin, nums2RightMin)// 的判斷,所以將它設置為int的最大值int nums1RightMin = i == leftLength ? Integer.MAX_VALUE : nums1[i];// 當j=0時,說明第二個數組分割線左邊沒有值,為了不影響// nums2[j - 1] <= nums1[i] 和 Math.max(nums1LeftMax, nums2LeftMax)// 的判斷,所以將它設置為int的最小值int nums2LeftMax = j == 0 ? Integer.MIN_VALUE : nums2[j - 1];// 等j=第二個數組的長度時,說明第二個數組分割線右邊沒有值,為了不影響// nums1[i - 1] <= nums2[j] 和 Math.min(nums1RightMin, nums2RightMin)// 的判斷,所以將它設置為int的最大值int nums2RightMin = j == rightLength ? Integer.MAX_VALUE : nums2[j];// 如果兩個數組的長度之和為奇數,直接返回兩個數組在分割線左邊的最大值即可if (((leftLength + rightLength) % 2) == 1) {return Math.max(nums1LeftMax, nums2LeftMax);} else {// 如果兩個數組的長度之和為偶數,返回的是兩個數組在左邊的最大值和兩個數組在右邊的最小值的和的二分之一// 此處不能被向下取整,所以要強制轉換為double類型return (double) ((Math.max(nums1LeftMax, nums2LeftMax) + Math.min(nums1RightMin, nums2RightMin))) / 2;}} }

【總結】

1. 二分查找法 log復雜度
2.邊界復雜 多種情況 腦袋清晰
3.時間算法復雜度可以讓簡單題變復雜題

轉載鏈接:https://leetcode-cn.com/problems/median-of-two-sorted-arrays/solution/xiang-xi-tong-su-de-si-lu-fen-xi-duo-jie-fa-by-w-2/
參考視頻與評論:https://leetcode-cn.com/problems/median-of-two-sorted-arrays/solution/xun-zhao-liang-ge-you-xu-shu-zu-de-zhong-wei-s-114/

總結

以上是生活随笔為你收集整理的[Leedcode][JAVA][第4题][寻找两个正序数组中的中位数][二分查找][双指针]的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。

主站蜘蛛池模板: 伊人热久久| 日韩欧美一区二区免费 | 亚洲成人一区二区 | 狠狠躁日日躁夜夜躁2022麻豆 | 日韩操操操 | а√天堂www在线天堂小说 | 欧美成人综合色 | 欧美bbbbbbbbbbbb1 麻豆精品av | 国产女厕一区二区三区在线视 | 亚洲天天做 | 久久精品欧美视频 | 男女一起插插插 | 国产精品久久久久久久久久辛辛 | 老司机一区二区三区 | 超碰精品在线观看 | 国产传媒中文字幕 | 日本黄色免费 | 91久久国产综合久久91 | 久久阁 | 成人精品一区二区 | 三点尽露的大尺度国产 | 秋霞成人午夜伦在线观看 | 欧美黑人性xxx猛交 少妇无套内谢久久久久 | 亚洲欧美另类中文字幕 | 好好热视频| 欧美色xxx| 中国美女洗澡免费看网站 | 国内精品视频在线播放 | av网址在线 | 亚洲第一视频区 | 新天堂网 | 中国一级免费毛片 | 天天碰天天碰 | 丝袜老师扒开让我了一夜漫画 | 日韩怡春院 | 久久嫩草| www.奇米 | 金瓶狂野欧美性猛交xxxx | 久久瑟瑟 | 老司机精品福利导航 | 自拍偷拍亚洲欧洲 | 欧美一区国产一区 | 一本色道综合久久欧美日韩精品 | 国产精品天天av精麻传媒 | 123毛片 | 在线免费观看 | 噜噜噜在线| 无遮挡的裸体按摩的视频 | 国产一区二区视频在线 | 欧美亚洲国产一区 | 亚洲剧情av | 丰满熟妇人妻中文字幕 | 日批视频免费看 | 西西人体大胆4444ww张筱雨 | 国产成人精品一区二区三区 | 久久久视屏 | 少妇人妻偷人精品无码视频新浪 | 亚洲一区二区在线 | 日韩精品成人在线 | 俄罗斯美女一级爱片 | 在线亚洲区 | 日韩网站在线播放 | 五月天婷婷丁香花 | 四虎在线免费 | 久久久久久免费 | 污污视频网站在线免费观看 | 男女超爽视频免费播放 | 午夜私人福利 | 成人在线视频在线观看 | 91久久免费| 日韩欧美国产网站 | 成人在线手机视频 | 免费国产一区二区 | 99久久夜色精品国产亚洲 | 中文在线观看视频 | 高清乱码免费看污 | 又黄又爽网站 | 黄色免费在线播放 | 二区国产 | 超碰爱爱| 欧美多p| 婷婷五月综合激情 | 蜜桃臀av | a√在线观看| 国产免费一区二区三区三州老师 | 青草视频在线 | 午夜88| a级特黄视频 | 久久久久久99精品久久久 | 日韩av中文字幕在线播放 | 日韩大尺度在线观看 | 乳女教师の诱惑julia | 日韩国产欧美视频 | 91秘密入口 | 国产免费一区二区三区四区五区 | 69式视频| 深爱开心激情 | 中文字幕在线观看第一页 | 又黄又爽的视频在线观看 |