两数组中位数
leetcode 4----兩數(shù)組中位數(shù)
解法(一)
通過(guò)新建數(shù)組的辦法,將兩個(gè)數(shù)組合并成一個(gè),然后找中位數(shù),代碼容易理解,但不是很快并且有點(diǎn)浪費(fèi)空間。
public double findMedianSortedArrays(int[] nums1, int[] nums2) {int len = nums1.length+nums2.length;int i = 0,j = 0,k=0;while(i<nums1.length && j<nums2.length){if(nums1[i]<=nums2[j]) arr[k++] = nums1[i++];else arr[k++] = nums2[j++];}while(i<nums1.length) arr[k++] = nums1[i++];while(j<nums2.length) arr[k++] = nums2[j++];if(len%2 == 0){int mid =len/2;return (arr[mid-1]+arr[mid])/2.0;}else{double mid = len/2.0;return (double)arr[(int)Math.ceil(mid)-1];}}解法(二)
首先計(jì)算中位數(shù),然后兩數(shù)組一個(gè)一個(gè)比較,并統(tǒng)計(jì)比較個(gè)數(shù),當(dāng)比較個(gè)數(shù)到中位數(shù)位置,直接獲取中位數(shù)的數(shù)數(shù)據(jù),然后進(jìn)行計(jì)算。
//計(jì)算中位數(shù)public double getmidnumber(int[] nums1, int[] nums2,int i,int j){int result = 0;//再判斷兩次即可if(nums1[i]<=nums2[j]) result += nums1[i++]; else result += nums2[j++];if(i<nums1.length && j<nums2.length){if(nums1[i]<=nums2[j]) result += nums1[i++]; else result += nums2[j++];return result/2.0;}if(i<nums1.length) {result += nums1[i++]; return result/2.0;}if(j<nums2.length) {result += nums2[j++]; return result/2.0;}return result/2.0;}public double findMedianSortedArrays(int[] nums1, int[] nums2) {int len = nums1.length+nums2.length;int i = 0,j = 0,k=0;//判斷長(zhǎng)度是奇數(shù)還是偶數(shù)if(len%2 == 0){int mid =len/2;//中位數(shù)在分別兩個(gè)數(shù)組while(i<nums1.length && j<nums2.length){//到達(dá)中位數(shù)的下標(biāo)if(k == mid-1)return getmidnumber(nums1,nums2,i,j);//根據(jù)大小移動(dòng)if(nums1[i]<=nums2[j]) i++;else j++;k++;}//清理剩余的//中位數(shù)的位置在nums1if(i<nums1.length)return (nums1[i+mid-1-k]+nums1[i+mid-k])/2.0;//中位數(shù)的位置在nums2elsereturn (nums2[j+mid-1-k]+nums2[j+mid-k])/2.0;}else{//奇數(shù)直接除二就能拿到那個(gè)中位數(shù)下標(biāo)int midindex = len/2;//中位數(shù)在分別兩個(gè)數(shù)組while(i<nums1.length && j<nums2.length){//到達(dá)中位數(shù)的下標(biāo)if(k == midindex)return nums1[i]<nums2[j]?nums1[i]:nums2[j];//根據(jù)大小移動(dòng)if(nums1[i]<=nums2[j]) i++;else j++;k++;}//清理剩余的//中位數(shù)的位置在nums1if(i<nums1.length)return nums1[i+midindex-k];elsereturn nums2[j+midindex-k];}}解法(三)
通過(guò)遞歸跳躍實(shí)現(xiàn)尋找中位數(shù),首先計(jì)算出中位數(shù)要跳躍的距離,然后根據(jù)距離每次折半進(jìn)行跳躍,從而漸漸逼近中位數(shù)。
public double findMedianSortedArrays(int[] nums1, int[] nums2) {int m = nums1.length;int n = nums2.length;//計(jì)算中位數(shù)位置,如果m+n等于奇數(shù)的話left==rightint left = (m + n + 1) / 2;int right = (m + n + 2) / 2;return (findKth(nums1, 0, nums2, 0, left) + findKth(nums1, 0, nums2, 0, right)) / 2.0;}//i: nums1的起始位置 j: nums2的起始位置//k: 是距離public int findKth(int[] nums1, int i, int[] nums2, int j, int k){if( i >= nums1.length) return nums2[j + k - 1];//nums1為空數(shù)組if( j >= nums2.length) return nums1[i + k - 1];//nums2為空數(shù)組//到達(dá)位置后,判斷if(k == 1){return Math.min(nums1[i], nums2[j]);}//跳躍,如果越界,用int的最大值表示無(wú)法進(jìn)行跳躍int midVal1 = (i + k / 2 - 1 < nums1.length) ? nums1[i + k / 2 - 1] : Integer.MAX_VALUE;int midVal2 = (j + k / 2 - 1 < nums2.length) ? nums2[j + k / 2 - 1] : Integer.MAX_VALUE;//判斷往哪邊進(jìn)行跳躍,并縮短跳躍距離,漸漸逼近中位數(shù)//往小的方向進(jìn)行跳躍,這樣可以避免跳過(guò)中位數(shù)的情況if(midVal1 < midVal2){return findKth(nums1, i + k / 2, nums2, j , k - k / 2);}else{return findKth(nums1, i, nums2, j + k / 2 , k - k / 2);} } }總結(jié)
- 上一篇: 使用Socket模拟聊天室
- 下一篇: HashMap解析