Find median in row wise sorted matrix - GeeksforGeeks

21 Feb, 2022
We are given a row-wise sorted matrix of size r*c, we need to find the median of the matrix given. It is assumed that r*c is always odd.Examples: 
Input : 1 3 5
        2 6 9
        3 6 9
Output : Median is 5
If we put all the values in a sorted 
array A[] = 1 2 3 3 5 6 6 9 9)

Input: 1 3 4
       2 5 6
       7 8 9
Output: Median is 5
Simple Method: The simplest method to solve this problem is to store all the elements of the given matrix in an array of size r*c. Then we can either sort the array and find the median element in O(r*clog(r*c)) or we can use the approach discussed here to find the median in O(r*c). Auxiliary space required will be O(r*c) in both cases.An efficient approach for this problem is to use a binary search algorithm. The idea is that for a number to be median there should be exactly (n/2) numbers that are less than this number. So, we try to find the count of numbers less than all the numbers. Below is the step by step algorithm for this approach: Algorithm:  
First, we find the minimum and maximum elements in the matrix. The minimum element can be easily found by comparing the first element of each row, and similarly, the maximum element can be found by comparing the last element of each row.Then we use binary search on our range of numbers from minimum to maximum, we find the mid of the min and max and get a count of numbers less than or equal to our mid. And accordingly change the min or max.For a number to be median, there should be (r*c)/2 numbers smaller than that number. So for every number, we get the count of numbers less than that by using upper_bound() in each row of the matrix, if it is less than the required count, the median must be greater than the selected number, else the median must be less than or equal to the selected number.
First, we find the minimum and maximum elements in the matrix. The minimum element can be easily found by comparing the first element of each row, and similarly, the maximum element can be found by comparing the last element of each row.
Then we use binary search on our range of numbers from minimum to maximum, we find the mid of the min and max and get a count of numbers less than or equal to our mid. And accordingly change the min or max.
For a number to be median, there should be (r*c)/2 numbers smaller than that number. So for every number, we get the count of numbers less than that by using upper_bound() in each row of the matrix, if it is less than the required count, the median must be greater than the selected number, else the median must be less than or equal to the selected number.
Below is the implementation of the above approach: 
C++
Java
Python3
C#
Javascript
// C++ program to find median of a matrix// sorted row wise#include<bits/stdc++.h>using namespace std; const int MAX = 100; // function to find median in the matrixint binaryMedian(int m[][MAX], int r ,int c){    int min = INT_MAX, max = INT_MIN;    for (int i=0; i<r; i++)    {        // Finding the minimum element        if (m[i][0] < min)            min = m[i][0];         // Finding the maximum element        if (m[i][c-1] > max)            max = m[i][c-1];    }     int desired = (r * c + 1) / 2;    while (min < max)    {        int mid = min + (max - min) / 2;        int place = 0;         // Find count of elements smaller than mid        for (int i = 0; i < r; ++i)            place += upper_bound(m[i], m[i]+c, mid) - m[i];        if (place < desired)            min = mid + 1;        else            max = mid;    }    return min;} // driver program to check above functionsint main(){    int r = 3, c = 3;    int m[][MAX]= { {1,3,5}, {2,6,9}, {3,6,9} };    cout << "Median is " << binaryMedian(m, r, c) << endl;    return 0;}
// Java program to find median of a matrix// sorted row wiseimport java.util.Arrays; public class MedianInRowSorted{    // function to find median in the matrix    static int binaryMedian(int m[][],int r, int c)    {        int max = Integer.MIN_VALUE;        int min = Integer.MAX_VALUE;                 for(int i=0; i<r ; i++)        {                         // Finding the minimum element            if(m[i][0] < min)                min = m[i][0];                         // Finding the maximum element            if(m[i][c-1] > max)                max = m[i][c-1];        }                 int desired = (r * c + 1) / 2;        while(min < max)        {            int mid = min + (max - min) / 2;            int place = 0;            int get = 0;                         // Find count of elements smaller than mid            for(int i = 0; i < r; ++i)            {                                 get = Arrays.binarySearch(m[i],mid);                                 // If element is not found in the array the                // binarySearch() method returns                // (-(insertion_point) - 1). So once we know                // the insertion point we can find elements                // Smaller than the searched element by the                // following calculation                if(get < 0)                    get = Math.abs(get) - 1;                                 // If element is found in the array it returns                // the index(any index in case of duplicate). So we go to last                // index of element which will give  the number of                // elements smaller than the number including                // the searched element.                else                {                    while(get < m[i].length && m[i][get] == mid)                        get += 1;                }                                 place = place + get;            }                         if (place < desired)                min = mid + 1;            else                max = mid;        }        return min;    }         // Driver Program to test above method.    public static void main(String[] args)    {        int r = 3, c = 3;        int m[][]= { {1,3,5}, {2,6,9}, {3,6,9} };                 System.out.println("Median is " + binaryMedian(m, r, c));    }} // This code is contributed by Sumit Ghosh
# Python program to find median of matrix# sorted row wise from bisect import bisect_right as upper_bound MAX = 100; # Function to find median in the matrixdef binaryMedian(m, r, d):    mi = m[0][0]    mx = 0    for i in range(r):        if m[i][0] < mi:            mi = m[i][0]        if m[i][d-1] > mx :            mx =  m[i][d-1]         desired = (r * d + 1) // 2         while (mi < mx):        mid = mi + (mx - mi) // 2        place = [0];                 # Find count of elements smaller than mid        for i in range(r):             j = upper_bound(m[i], mid)             place[0] = place[0] + j        if place[0] < desired:            mi = mid + 1        else:            mx = mid    print ("Median is", mi)    return        # Driver coder, d = 3, 3 m = [ [1, 3, 5], [2, 6, 9], [3, 6, 9]]binaryMedian(m, r, d) # This code is contributed by Sachin BIsht
// C# program to find median// of a matrix sorted row wiseusing System;class MedianInRowSorted{ // Function to find median// in the matrixstatic int binaryMedian(int [,]m,                        int r, int c){  int max = int.MinValue;  int min = int.MaxValue;   for(int i = 0; i < r; i++)  {    // Finding the minimum    // element    if(m[i, 0] < min)      min = m[i, 0];     // Finding the maximum    // element    if(m[i, c - 1] > max)      max = m[i, c - 1];  }   int desired = (r * c + 1) / 2;  while(min < max)  {    int mid = min + (max - min) / 2;    int place = 0;    int get = 0;     // Find count of elements    // smaller than mid    for(int i = 0; i < r; ++i)    {      get = Array.BinarySearch(            GetRow(m, i), mid);       // If element is not found      // in the array the binarySearch()      // method returns (-(insertion_      // point) - 1). So once we know      // the insertion point we can      // find elements Smaller than      // the searched element by the      // following calculation      if(get < 0)        get = Math.Abs(get) - 1;       // If element is found in the      // array it returns the index(any      // index in case of duplicate). So      // we go to last index of element      // which will give  the number of      // elements smaller than the number      // including the searched element.      else      {        while(get < GetRow(m, i).GetLength(0) &&              m[i, get] == mid)          get += 1;      }       place = place + get;    }     if (place < desired)      min = mid + 1;    else      max = mid;  }  return min;} public static int[] GetRow(int[,] matrix,                           int row){  var rowLength = matrix.GetLength(1);  var rowVector = new int[rowLength];   for (var i = 0; i < rowLength; i++)    rowVector[i] = matrix[row, i];   return rowVector;}   // Driver codepublic static void Main(String[] args){  int r = 3, c = 3;  int [,]m = {{1,3,5},              {2,6,9},              {3,6,9} };   Console.WriteLine("Median is " +                     binaryMedian(m, r, c));}} // This code is contributed by Princi Singh
<script> // Javascript program to find median// of a matrix sorted row wise  // Function to find median// in the matrixfunction binaryMedian(m, r, c){  var max = -1000000000;  var min = 1000000000;   for(var i = 0; i < r; i++)  {    // Finding the minimum    // element    if(m[i][0] < min)      min = m[i][0];     // Finding the maximum    // element    if(m[i] > max)      max = m[i];  }   var desired =  parseInt((r * c + 1) / 2);  while(min < max)  {    var mid = min + parseInt((max - min) / 2);    var place = 0;    var get = 0;     // Find count of elements    // smaller than mid    for(var i = 0; i < r; ++i)    {        var tmp = GetRow(m, i);        for(var j = tmp.length; j>=0; j--)        {            if(tmp[j] <= mid)            {                get = j+1;                break;            }        }       // If element is not found      // in the array the binarySearch()      // method returns (-(insertion_      // point) - 1). So once we know      // the insertion point we can      // find elements Smaller than      // the searched element by the      // following calculation      if(get < 0)        get = Math.abs(get) - 1;       // If element is found in the      // array it returns the index(any      // index in case of duplicate). So      // we go to last index of element      // which will give  the number of      // elements smaller than the number      // including the searched element.      else      {        while(get < GetRow(m, i).length &&              m[i][get] == mid)          get += 1;      }       place = place + get;    }     if (place < desired)      min = mid + 1;    else      max = mid;  }  return min;} function GetRow(matrix, row){  var rowLength = matrix[0].length;  var rowVector = Array(rowLength).fill(0);   for (var i = 0; i < rowLength; i++)    rowVector[i] = matrix[row][i];   return rowVector;}   // Driver codevar r = 3, c = 3;var m = [[1,3,5],            [2,6,9],            [3,6,9]];document.write("Median is " +                   binaryMedian(m, r, c));  // This code is contributed by rutvik_56.</script>
Median is 5
Time Complexity: O(32 * r * log(c)). The upper bound function will take log(c) time and is performed for each row. And since the numbers will be max of 32 bit, so binary search of numbers from min to max will be performed in at most 32 ( log2(2^32) = 32 ) operations. Auxiliary Space: O(1)  
YouTubeGeeksforGeeks500K subscribersFind median of a row-wise sorted Matrix | GeeksforGeeksWatch laterShareCopy linkInfoShoppingTap to unmuteIf playback doesn't begin shortly, try restarting your device.You're signed outVideos you watch may be added to the TV's watch history and influence TV recommendations. To avoid this, cancel and sign in to YouTube on your computer.CancelConfirmMore videosMore videosSwitch cameraShareInclude playlistAn error occurred while retrieving sharing information. Please try again later.Watch on0:000:000:00 / 11:48•Live•<div class="player-unavailable"><h1 class="message">An error occurred.</h1><div class="submessage"><a href="https://www.youtube.com/watch?v=_4rxBuhyLXw" target="_blank">Try watching this video on www.youtube.com</a>, or enable JavaScript if it is disabled in your browser.</div></div>
This article is contributed by Akshit Agarwal. If you like GeeksforGeeks and would like to contribute, you can also write an article using write.geeksforgeeks.org or mail your article to review-team@geeksforgeeks.org. See your article appearing on the GeeksforGeeks main page and help other Geeks.Please write comments if you find anything incorrect, or you want to share more information about the topic discussed above. 
laveena14
sajal10798
princi singh
rutvik_56
2019285
walterwhitejunior
Binary Search
median-finding
Order-Statistics
statistical-algorithms
Matrix
Matrix
Binary Search
Writing code in comment?
Please use ide.geeksforgeeks.org,
generate link and share the link here.
Comments
Old Comments
Matrix Chain Multiplication | DP-8
Program to find largest element in an array
Print a given matrix in spiral form
Sudoku | Backtracking-7
Rat in a Maze | Backtracking-2
Divide and Conquer | Set 5 (Strassen's Matrix Multiplication)
Program to multiply two matrices
Find the number of islands | Set 1 (Using DFS)
The Celebrity Problem
Min Cost Path | DP-6