Count elements smaller than or equal to x in a sorted matrix

Given a n x n strictly sorted matrix and a value x. The problem is to count the elements smaller than or equal to x in the given matrix. Here strictly sorted matrix means that matrix is sorted in a way such that all elements in a row are sorted in increasing order and for row ‘i’, where 1 <= i <= n-1, first element of row 'i' is greater than or equal to the last element of row 'i-1'.

Examples:

Input : mat[][] = { {1, 4, 5},
                    {6, 10, 11},
                    {12, 15, 20} }
       x = 9
Output : 4
The elements smaller than '9' are:
1, 4, 5 and 6.

Input : mat[][] = { {1, 4, 7, 8},
                {10, 10, 12, 14},
            {15, 26, 30, 31},
            {31, 42, 46, 50} }
        x = 31
Output : 13

Naive Approach: Traverse the matrix using two nested loops and count the elements smaller than or equal to x. Time Complexity is of O(n^2).

Efficient Approach: As matrix is strictly sorted, use the concept of binary search technique. First apply the binary search technique on the elements of the first column to find the row index number of the largest element smaller than equal to ‘x’. For duplicates get the last row index no of occurrence of required element ‘x’. Let it be row_no.. If no such row exists then return 0. Else apply the concept of binary search technique to find the column index no of the largest element smaller than or equal to ‘x’ in the row represented by row_no. Let it col_no. Finally return ((row_no) * n) + (col_no + 1). The concept of binary search technique can be understood by the binary_search function of this post.

C++

filter_none

edit
close

play_arrow

link
brightness_4
code

// C++ implementation to count elements smaller than
// or equal to x in a sorted matrix
#include <bits/stdc++.h>
  
using namespace std;
  
#define SIZE 100
  
// function returns the row index no of largest element
// smaller than equal to 'x' in first column of mat[][].
// For duplicates it returns the last row index no of
// occurrence of required element 'x'. If no such element
// exits then it returns -1.
int binarySearchOnRow(int mat[SIZE][SIZE],
                      int l, int h, int x)
{
    while (l <= h) {
        int mid = (l + h) / 2;
  
        // if 'x' is greater than or equal to mat[mid][0],
        // then search in mat[mid+1...h][0]
        if (mat[mid][0] <= x)
            l = mid + 1;
  
        // else search in mat[l...mid-1][0]
        else
            h = mid - 1;
    }
  
    // required row index number
    return h;
}
  
// function returns the column index no of largest element
// smaller than equal to 'x' in mat[row][].
// For duplicates it returns the last column index no of
// occurrence of required element 'x'.
int binarySearchOnCol(int mat[SIZE][SIZE],
                      int l, int h, int x, int row)
{
    while (l <= h) {
        int mid = (l + h) / 2;
  
        // if 'x' is greater than or equal to mat[row][mid],
        // then search in mat[row][mid+1...h]
        if (mat[row][mid] <= x)
            l = mid + 1;
  
        // else search in mat[row][l...mid-1]
        else
            h = mid - 1;
    }
  
    // required column index number
    return h;
}
  
// function to count elements smaller than
// or equal to x in a sorted matrix
int countSmallElements(int mat[SIZE][SIZE],
                       int n, int x)
{
    // to get the row index number of the largest element
    // smaller than equal to 'x' in mat[][]
    int row_no = binarySearchOnRow(mat, 0, n - 1, x);
  
    // if no such row exists
    if (row_no == -1)
        return 0;
  
    // to get the column index number of the largest element
    // smaller than equal to 'x' in mat[row_no][]
    int col_no = binarySearchOnCol(mat, 0, n - 1, x, row_no);
  
    // required count of elements
    return ((row_no)*n) + (col_no + 1);
}
  
// Driver program to test above
int main()
{
    int mat[SIZE][SIZE] = { { 1, 4, 7, 8 },
                            { 10, 10, 12, 14 },
                            { 15, 26, 30, 31 },
                            { 31, 42, 46, 50 } };
    int n = 4;
    int x = 31;
    cout << "Count = "
         << countSmallElements(mat, n, x);
    return 0;
}

chevron_right


Java

filter_none

edit
close

play_arrow

link
brightness_4
code

//Java implementation to count elements 
// smaller than or equal to x in a sorted matrix
import java.io.*;
  
class GFG {
  
static int SIZE=100;
  
// function returns the row index 
//no of largest element smaller than 
// equal to 'x' in first column of 
//mat[][].For duplicates it returns
//the last row index no of
// occurrence of required element
// 'x'. If no such element
// exits then it returns -1.
static int binarySearchOnRow(int[][] mat,
                        int l, int h, int x)
{
    while (l <= h) {
      
        int mid = (l + h) / 2;
  
        // if 'x' is greater than or 
        // equal to mat[mid][0],then 
        // search in mat[mid+1...h][0]
        if (mat[mid][0] <= x)
            l = mid + 1;
  
        // else search in mat[l...mid-1][0]
        else
            h = mid - 1;
    }
  
    // required row index number
    return h;
}
  
// function returns the column index
// no of largest element
// smaller than equal to 'x' in 
// mat[row][].For duplicates it returns
// the last column index no of
// occurrence of required element 'x'.
static int binarySearchOnCol(int[][] mat,
                    int l, int h, int x, int row)
{
    while (l <= h) {
        int mid = (l + h) / 2;
  
        // if 'x' is greater than or 
        // equal to mat[row][mid], then 
        // search in mat[row][mid+1...h]
        if (mat[row][mid] <= x)
            l = mid + 1;
  
        // else search in mat[row][l...mid-1]
        else
            h = mid - 1;
    }
  
    // required column index number
    return h;
}
  
// function to count elements smaller than
// or equal to x in a sorted matrix
static int countSmallElements(int[][] mat,
                                int n, int x)
{
    // to get the row index number of the largest 
    // element smaller than equal to 'x' in mat[][]
    int row_no = binarySearchOnRow(mat, 
                            0, n - 1, x);
  
    // if no such row exists
    if (row_no == -1)
        return 0;
  
    // to get the column index number of  
    // the largest element smaller than 
    // equal to 'x' in mat[row_no][]
    int col_no = binarySearchOnCol(mat,
                        0, n - 1, x, row_no);
  
    // required count of elements
    return ((row_no) * n) + (col_no + 1);
}
  
  
// Driver code
    public static void main (String[] args) {
        int mat[][] =      { { 1, 4, 7, 8 },
                            { 10, 10, 12, 14 },
                            { 15, 26, 30, 31 },
                            { 31, 42, 46, 50 } };
    int n = 4;
    int x = 31;
    System.out.println("Count = "
                + countSmallElements(mat, n, x));
      
    }
}
// This code is contributed by Gitanjali.

chevron_right


Python3

filter_none

edit
close

play_arrow

link
brightness_4
code

# Python implementation to
# count elements smaller than
# or equal to x in a sorted matrix
  
SIZE = 100
  
# function returns the row index
# no of largest element
# smaller than equal to 'x' in
# first column of mat[][].
# For duplicates it returns the
# last row index no of
# occurrence of required element
# 'x'. If no such element
# exits then it returns -1.
def binarySearchOnRow(mat, l, h, x):
    while l <= h:
        mid = (l + h) // 2
  
        # if 'x' is greater than or
        # equal to mat[mid][0],
        # then search in mat[mid+1...h][0]
        if mat[mid][0] <= x:
            l = mid + 1
  
        # else search in mat[l...mid-1][0]
        else:
            h = mid - 1
  
    # required row index number
    return h
  
# function returns the column
# index no of largest element
# smaller than equal to 'x'
# in mat[row][].
# For duplicates it returns the
# last column index no of
# occurrence of required element 'x'.
def binarySearchOnCol(mat, l, h, x, row):
    while l <= h:
        mid = (l + h) // 2
  
        # if 'x' is greater than or
        # equal to mat[row][mid],
        # then search in mat[row][mid+1...h]
        if mat[row][mid] <= x:
            l = mid + 1
  
        # else search in mat[row][l...mid-1]
        else:
            h = mid - 1
  
    # required column index number
    return h
  
# function to count elements smaller than
# or equal to x in a sorted matrix
def countSmallElements(mat, n, x):
    # to get the row index number
    # of the largest element
    # smaller than equal to 'x' in mat[][]
    row_no = binarySearchOnRow(mat, 0, n - 1, x)
  
    # if no such row exists
    if row_no == -1:
        return 0
  
    # to get the column index number
    # of the largest element
    # smaller than equal to 'x' in mat[row_no][]
    col_no = binarySearchOnCol(mat, 0,
                              n - 1, x, row_no)
  
    # required count of elements
    return ((row_no)*n) + (col_no + 1)
  
# Driver program to test above
mat = [ [ 1, 4, 7, 8 ],
        [ 10, 10, 12, 14 ],
        [ 15, 26, 30, 31 ],
        [ 31, 42, 46, 50 ] ]
n = 4
x = 31
print("Count = " + str(countSmallElements(mat, n, x)))
  
# This code is contributed by Ansu Kumari.

chevron_right


C#

filter_none

edit
close

play_arrow

link
brightness_4
code

//Java implementation to count elements 
// smaller than or equal to x in a sorted matrix
using System;
  
class GFG {
  
    //static int SIZE=100;
      
    // function returns the row index 
    //no of largest element smaller than 
    // equal to 'x' in first column of 
    //mat[][].For duplicates it returns
    //the last row index no of
    // occurrence of required element
    // 'x'. If no such element
    // exits then it returns -1.
    static int binarySearchOnRow(int [,] mat, int l,
                                 int h, int x)
    {
        while (l <= h) {
          
            int mid = (l + h) / 2;
      
            // if 'x' is greater than or 
            // equal to mat[mid][0],then 
            // search in mat[mid+1...h][0]
            if (mat[mid,0] <= x)
                l = mid + 1;
      
            // else search in mat[l...mid-1][0]
            else
                h = mid - 1;
        }
      
        // required row index number
        return h;
    }
      
    // function returns the column index
    // no of largest element
    // smaller than equal to 'x' in 
    // mat[row][].For duplicates it returns
    // the last column index no of
    // occurrence of required element 'x'.
    static int binarySearchOnCol(int [,]mat, int l,
                                   int h, int x, int row)
    {
        while (l <= h) {
            int mid = (l + h) / 2;
      
            // if 'x' is greater than or 
            // equal to mat[row][mid], then 
            // search in mat[row][mid+1...h]
            if (mat[row,mid] <= x)
                l = mid + 1;
      
            // else search in mat[row][l...mid-1]
            else
                h = mid - 1;
        }
      
        // required column index number
        return h;
    }
      
    // function to count elements smaller than
    // or equal to x in a sorted matrix
    static int countSmallElements(int[,] mat,
                                    int n, int x)
    {
        // to get the row index number of the largest 
        // element smaller than equal to 'x' in mat[][]
        int row_no = binarySearchOnRow(mat, 
                                 0, n - 1, x);
      
        // if no such row exists
        if (row_no == -1)
            return 0;
      
        // to get the column index number of 
        // the largest element smaller than 
        // equal to 'x' in mat[row_no][]
        int col_no = binarySearchOnCol(mat,
                     0, n - 1, x, row_no);
      
        // required count of elements
        return ((row_no) * n) + (col_no + 1);
    }
      
      
    // Driver code
    public static void Main () {
        int [,]mat =     { { 1, 4, 7, 8 },
                            { 10, 10, 12, 14 },
                            { 15, 26, 30, 31 },
                            { 31, 42, 46, 50 } };
        int n = 4;
        int x = 31;
        Console.WriteLine("Count = "
                         + countSmallElements(mat, n, x));
      
    }
}
  
// This code is contributed by vt_m.

chevron_right


PHP

filter_none

edit
close

play_arrow

link
brightness_4
code

<?php
// PHP implementation to count
// elements smaller than or 
// equal to x in a sorted matrix
  
// function returns the row index
// no of largest element smaller 
// than equal to 'x' in first 
// column of mat[][]. For duplicates
// it returns the last row index no. 
// of occurrence of required element
// 'x'. If no such element exits then
// it returns -1.
function binarySearchOnRow($mat, $l
                             $h, $x)
{
    while ($l <= $h) {
        $mid = floor(($l + $h) / 2);
  
        // if 'x' is greater than 
        // or equal to mat[mid][0],
        // then search in 
        // mat[mid+1...h][0]
        if ($mat[$mid][0] <= $x)
            $l = $mid + 1;
  
        // else search in
        // mat[l...mid-1][0]
        else
            $h = $mid - 1;
    }
  
    // required row index number
    return $h;
}
  
// function returns the column
// index no of largest element
// smaller than equal to 'x' 
// in mat[row][]. For duplicates
// it returns the last column 
// index no of occurrence of 
// required element 'x'.
function binarySearchOnCol($mat, $l
                       $h, $x, $row)
{
    while ($l <= $h) {
        $mid = floor(($l + $h) / 2);
  
        // if 'x' is greater than or
        // equal to mat[row][mid],
        // then search in 
        // mat[row][mid+1...h]
        if ($mat[$row][$mid] <= $x)
            $l = $mid + 1;
  
        // else search in 
        // mat[row][l...mid-1]
        else
            $h = $mid - 1;
    }
  
    // required column
    // index number
    return $h;
}
  
// function to count elements
// smaller than or equal to x
// in a sorted matrix
function countSmallElements($mat,
                           $n, $x)
{
      
    // to get the row index number
    // of the largest element
    // smaller than equal to 'x' 
    // in mat[][]
    $row_no = binarySearchOnRow($mat, 0,
                            $n - 1, $x);
  
    // if no such row exists
    if ($row_no == -1)
        return 0;
  
    // to get the column index
    // number of the largest element
    // smaller than equal to 'x' 
    // in mat[row_no][]
    $col_no = binarySearchOnCol($mat, 0, 
                    $n - 1, $x, $row_no);
  
    // required count of elements
    return floor(($row_no) * $n) + 
                     ($col_no + 1);
}
  
    // Driver Code
    $mat = array(array(1, 4, 7, 8),
                 array(10, 10, 12, 14),
                 array(15, 26, 30, 31),
                 array(31, 42, 46, 50));
    $n = 4;
    $x = 31;
    echo "Count = ", countSmallElements ($mat, $n, $x);
      
// This code is contributed by nitin mittal.
?>

chevron_right



Output:

Count = 13

Time Complexity: O(Log2n).



My Personal Notes arrow_drop_up

Check out this Author's contributed articles.

If you like GeeksforGeeks and would like to contribute, you can also write an article using contribute.geeksforgeeks.org or mail your article to contribute@geeksforgeeks.org. See your article appearing on the GeeksforGeeks main page and help other Geeks.

Please Improve this article if you find anything incorrect by clicking on the "Improve Article" button below.



Improved By : nitin mittal