Problem: Find k-th largest (or Median) in two sorted arrays
Solution 1
=========
Suppose input array's are in the following fashion
A[] = {2, 3, 7, 12, 27, 81, 91}
b[] = {1, 25, 32, 74, 89}
1. Take two pointers ptr1 and ptr2 at start in A[] and B[]
2. if(A[i] > B[j])
j++;
else
i++;
3. if ( (i +j ) == k)
compare A[i] and B[j] and return the larger of them
else
repeat step2.
Time Complexity = O(k)
code:
int i=0;
int j=0;
while(i<A.length && j<B.length)
{
if(i+j+2 == k){
if(i == A.length) return B[j];
else if (j == B.length) return A[i];
else
return (A[i]>=B[j]?A[i]:B[j]);
}
if(i == A.length)j++;
else if (j == B.length)i++;
else if(A[i]>=B[j])i++;
else
j++;
}
Solution2
==========
Idea = We have to find the median of first k elements of A and B and k = 5
1. The kth largest among the union of A[] and B[] would be in the first k elements of of A[] and b[]
2. Consider k elements from A[] and B[] which results in the following array
a[] = {2. 3, 7, 12, 27}
b[] = {1, 25, 32, 74, 89}
3. Compare (A[mid], B[mid])
if (A[mid] is GT)
{
For ArrayA = We can skip a[mid]..a[k] elements since a[mid] is greater and all elements from a[0]..a[mid] are valid candidates for being the median; since A[mid] is the greater element no point considering bigger elements than that for the median
For Array B = We can skip b[0]...b[mid] elements since b[mid] is less; so all elements less than are not valid candidates for being median.
}
4. Repeat Step3 till you are left with either 2 or 3 elements then you do a comparision and find kth largest.
Time Complexity = O(log k)
Example showing Solution 2
=========================
A[] = { 2, 3, 7, 12, 27}
B[] = {1, 25, 32, 75, 89}
After step2 i.e. k elements from both arrays
A[mid] = 7 and B[mid] = 32
B[mid] is Greater.
Now array becomes after step3
a[] = {7, 12, 27}
b[] = { 1, 25, 32}
a[mid] = 12 and b[mid] = 25
After step3 the arrays become
a[] = { 12, 27} -- skpping the left portion of smaller element array
b[] = { 1, 25} -- skipping the right portion of larger element array
Now a[mid] = 12 and b[mid] = 1
after step3 the array becomes
a[] = {12}
b[] = {1,25}
Find the median of 12, 1, 25 in O(1) which is 12 which is the 5th largest
code(find median):
median(int* A, int * B, int sa, int sb)
{
int mid_a = sa/2-1;
int mid_b = sb/2-1;
if(sa == 0)return B[mid_b];
else if(sb == 0)return A[mid_a];
else if(A[mid_a] == B[mid_b])return A[mid_a];
if(A[mid_a] > B[mid_b])
return(A, B+mid_b+1, mid_a, (sb-mid_b-1));
else{
return(A+mid_a+1, B, (sa-mid_a-1),mid_b );
}
}
another code in C:
1
2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 |
#include <stdio.h>
/* select: gets two sorted positive integer arrays, a & b, with sizes sa & sb respectively, and returns the k-th smallest element of their union. smallest element is referenced with k = 1 returns -1 on error */ int select ( int * a , int * b , int sa , int sb , int k ) { int ma = sa < k / 2 ? sa - 1 : k / 2 - 1 ; int mb = k - ma - 2 ; if ( sa + sb < k ) return - 1 ; if ( sa == 0 ) return b [ k - 1 ] ; if ( sb == 0 ) return a [ k - 1 ] ; if ( k == 1 ) return a [ 0 ] < b [ 0 ] ? a [ 0 ] : b [ 0 ] ; if ( a [ ma ] == b [ mb ] ) return a [ ma ] ; if ( a [ ma ] < b [ mb ] ) return select ( a + ma + 1 , b , sa - ma - 1 , mb + 1 , k - ma - 1 ) ; return select ( a , b + mb + 1 , ma + 1 , sb - mb - 1 , k - mb - 1 ) ; } /* median: uses select to find the median of the union of a and b (where a and b are sorted positive integer arrays of sizes sa and sb respectively. */ int median ( int * a , int * b , int sa , int sb ) { int m1 , m2 ; if ( ( sa + sb ) % 2 == 1 ) return select ( a , b , sa , sb , ( sa + sb ) / 2 + 1 ) ; m1 = select ( a , b , sa , sb , ( sa + sb ) / 2 ) ; m2 = select ( a , b , sa , sb , ( sa + sb ) / 2 + 1 ) ; return ( m1 + m2 ) / 2 ; } int main ( ) { int a [ 3 ] = { 2 , 4 , 6 } ; int b [ 11 ] = { 1 , 3 , 5 , 7 , 13 , 17 , 22 , 23 , 24 , 25 , 31 } ; printf ( "/n median is %d/n " , median ( a , b , 3 , 11 ) ) ; return 0 ; } |
源地址: http://inder-gnu.blogspot.com/2007/09/find-k-th-largest-in-two-sorted-arrays.html