Given an array arr[] of positive integers and an integer k, find the total number of pairs of elements that have an absolute difference strictly less than k. Pair (i, j) is considered the same as (j, i).
Examples:
Input: arr[] = [1, 10, 4, 2], k = 3
Output: 2
Explanation: We have an array arr[] = [1, 10, 4, 2] and k = 3 We can make only two pairs with a difference of less than 3. (1, 2) and (4, 2). So, the answer is 2.Input: arr[] = [2, 3, 4], k = 5
Output: 3
Explanation: For the given array arr[] = [2, 3, 4] and k = 5, there are 3 valid pairs where the absolute difference between the pair's elements is less than 5. These pairs are (2, 3), (2, 4), and (3, 4). Hence, the output is 3.
Table of Content
[Naive Approach] Using Nested loops - O(n^2) Time and O(1) Space
The idea is to run two nested loops. The outer loop picks every element x one by one. The inner loop considers all elements after x and checks if the difference is within limits or not.
Working of Approach:
- Initialize a counter and check every possible pair of elements using two nested loops.
- For each pair, calculate the absolute difference using abs(arr[j] - arr[i]).
- If the difference is less than k, increment the counter.
- Return the final counter as the number of valid pairs.
#include <bits/stdc++.h>
using namespace std;
int countPairs(vector<int> &arr, int k)
{
int res = 0;
int n = arr.size();
// Iterate through every possible pair
for (int i = 0; i < n; i++)
{
for (int j = i + 1; j < n; j++)
{
// If the absolute difference is strictly less than k, count it
if (abs(arr[j] - arr[i]) < k)
{
res++;
}
}
}
return res;
}
int main()
{
vector<int> arr = {1, 10, 4, 2};
int k = 3;
cout << countPairs(arr, k) << endl;
return 0;
}
import java.io.*;
class GFG {
public int countPairs(int[] arr, int k)
{
int res = 0;
int n = arr.length;
// Iterate through every possible pair
for (int i = 0; i < n; i++) {
for (int j = i + 1; j < n; j++) {
// If the absolute difference is strictly
// less than k, count it
if (Math.abs(arr[j] - arr[i]) < k) {
res++;
}
}
}
return res;
}
public static void main(String[] args)
{
int[] arr = { 1, 10, 4, 2 };
int k = 3;
GFG ob = new GFG();
System.out.println(ob.countPairs(arr, k));
}
}
# Python3 code to find count of pairs
# with difference less than K.
def countPairs(arr, k):
res = 0
n = len(arr)
# Iterate through every possible pair
for i in range(n):
for j in range(i + 1, n):
# If the absolute difference is strictly less than k, count it
if abs(arr[j] - arr[i]) < k:
res += 1
return res
if __name__ == "__main__":
arr = [1, 10, 4, 2]
k = 3
print(countPairs(arr, k))
using System;
class GFG {
public int countPairs(int[] arr, int k)
{
int res = 0;
int n = arr.Length;
// Iterate through every possible pair
for (int i = 0; i < n; i++) {
for (int j = i + 1; j < n; j++) {
// If the absolute difference is strictly
// less than k, count it
if (Math.Abs(arr[j] - arr[i]) < k) {
res++;
}
}
}
return res;
}
public static void Main()
{
int[] arr = { 1, 10, 4, 2 };
int k = 3;
GFG ob = new GFG();
Console.WriteLine(ob.countPairs(arr, k));
}
}
function countPairs(arr, k)
{
let res = 0;
let n = arr.length;
// Iterate through every possible pair
for (let i = 0; i < n; i++) {
for (let j = i + 1; j < n; j++) {
// If the absolute difference is strictly less
// than k, count it
if (Math.abs(arr[j] - arr[i]) < k) {
res++;
}
}
}
return res;
}
// Driver Code
let arr = [ 1, 10, 4, 2 ];
let k = 3;
console.log(countPairs(arr, k));
Output
2
[Better Approach] Using Sorting with Binary Search - O(n log n) Time and O(1) Space
The idea is to first sort the array and process each element one by one. For every element, use binary search to find the first element greater than or equal to arr[i] + k, and count all elements before it as valid pairs.
Working of Approach:
- Sort the array so that elements with smaller differences are grouped together, enabling binary search.
- For each element arr[i], find the first element greater than or equal to arr[i] + k using lower_bound().
- All elements between indices i + 1 and y - 1 form valid pairs with arr[i].
- Add these counts for every element and return the total number of valid pairs.
#include <bits/stdc++.h>
using namespace std;
int countPairs(vector<int> &arr, int k)
{
int n = arr.size();
// Sort the array in non-decreasing order
sort(arr.begin(), arr.end());
int res = 0;
// Iterate through each index
for (int i = 0; i < n; i++)
{
// val stores the threshold value; elements strictly less
// than val will have a difference with arr[i] less than k.
int val = arr[i] + k;
// Find the index of the first element in the array which is
// greater than or equal to val.
int y = lower_bound(arr.begin(), arr.end(), val) - arr.begin();
// Add the count of all valid pairs possible for the current arr[i]
res += (y - i - 1);
}
return res;
}
int main()
{
vector<int> arr = {1, 10, 4, 2};
int k = 3;
cout << countPairs(arr, k) << endl;
return 0;
}
import java.util.*;
public class GFG {
static int countPairs(int[] arr, int k)
{
int n = arr.length;
// Sort the array in non-decreasing order
Arrays.sort(arr);
int res = 0;
// Iterate through each index
for (int i = 0; i < n; i++) {
// val stores the threshold value; elements
// strictly less than val will have a difference
// with arr[i] less than k.
int val = arr[i] + k;
// Find the index of the first element in the
// array which is greater than or equal to val.
int y = Arrays.binarySearch(arr, val);
if (y < 0) {
y = -y - 1;
}
else {
while (y > 0 && arr[y - 1] == val) {
y--;
}
}
// Add the count of all valid pairs possible for
// the current arr[i]
res += (y - i - 1);
}
return res;
}
public static void main(String[] args)
{
int[] arr = { 1, 10, 4, 2 };
int k = 3;
System.out.println(countPairs(arr, k));
}
}
from bisect import bisect_left
def countPairs(arr, k):
n = len(arr)
# Sort the array in non-decreasing order
arr.sort()
res = 0
# Iterate through each index
for i in range(n):
# val stores the threshold value; elements strictly less
# than val will have a difference with arr[i] less than k.
val = arr[i] + k
# Find the index of the first element in the array which is
# greater than or equal to val.
y = bisect_left(arr, val)
# Add the count of all valid pairs possible for the current arr[i]
res += (y - i - 1)
return res
if __name__ == "__main__":
arr = [1, 10, 4, 2]
k = 3
print(countPairs(arr, k))
using System;
class GFG {
static int countPairs(int[] arr, int k)
{
int n = arr.Length;
// Sort the array in non-decreasing order
Array.Sort(arr);
int res = 0;
// Iterate through each index
for (int i = 0; i < n; i++) {
// val stores the threshold value; elements
// strictly less than val will have a difference
// with arr[i] less than k.
int val = arr[i] + k;
// Find the index of the first element in the
// array which is greater than or equal to val.
int y = Array.BinarySearch(arr, val);
if (y < 0) {
y = ~y;
}
else {
while (y > 0 && arr[y - 1] == val)
y--;
}
// Add the count of all valid pairs possible for
// the current arr[i]
res += (y - i - 1);
}
return res;
}
static void Main()
{
int[] arr = { 1, 10, 4, 2 };
int k = 3;
Console.WriteLine(countPairs(arr, k));
}
}
function lowerBound(arr, val)
{
let left = 0, right = arr.length;
while (left < right) {
let mid = Math.floor((left + right) / 2);
if (arr[mid] < val)
left = mid + 1;
else
right = mid;
}
return left;
}
function countPairs(arr, k)
{
let n = arr.length;
// Sort the array in non-decreasing order
arr.sort((a, b) => a - b);
let res = 0;
// Iterate through each index
for (let i = 0; i < n; i++) {
// val stores the threshold value; elements strictly
// less than val will have a difference with arr[i]
// less than k.
let val = arr[i] + k;
// Find the index of the first element in the array
// which is greater than or equal to val.
let y = lowerBound(arr, val);
// Add the count of all valid pairs possible for the
// current arr[i]
res += (y - i - 1);
}
return res;
}
// Driver Code
let arr = [ 1, 10, 4, 2 ];
let k = 3;
console.log(countPairs(arr, k));
Output
2
[Expected Approach] Using Sorting with Sliding Window - O(n log n) Time and O(1) Space
The idea is to sort the array and use two pointers, s and i, to maintain a sliding window. As the right pointer i traverses the array, advance the left pointer s forward until arr[i] - arr[s] < k. At this point, all elements between s and i-1 form valid pairs with arr[i], and we add i - s to our total count.
Let us understand with an example:
Input: arr[] = {1, 10, 4, 2}, k = 3
- After sorting, arr[] = {1, 2, 4, 10}.
- Initialize s = 0 and total = 0.
- For i = 1 (arr[i] = 2), 2 - 1 = 1 < 3, so add i - s = 1 to total. Now, total = 1.
- For i = 2 (arr[i] = 4), 4 - 1 = 3 >= 3, so increment s to 1. Now, 4 - 2 = 2 < 3, so add i - s = 1 to total. Now, total = 2.
- For i = 3 (arr[i] = 10), keep incrementing s while 10 - arr[s] >= 3. No valid pairs remain for this element.
Hence, the total number of pairs with absolute difference less than k is 2.
#include <bits/stdc++.h>
using namespace std;
int countPairs(vector<int> &arr, int k)
{
int n = arr.size();
// Sort the array in non-decreasing order
sort(arr.begin(), arr.end());
int total = 0;
int s = 0;
// Iterate with right pointer i
for (int i = 0; i < n; i++)
{
// Shrink the window from the left until
// the condition holds
while (arr[i] - arr[s] >= k)
{
s++;
}
// All elements between's' and 'i-1' form
// a valid pair with 'arr[i]'
total += (i - s);
}
return total;
}
int main()
{
vector<int> arr = {1, 10, 4, 2};
int k = 3;
cout << countPairs(arr, k) << endl;
return 0;
}
import java.util.*;
class GFG {
public int countPairs(int[] arr, int k)
{
// Sort the array in non-decreasing order
Arrays.sort(arr);
int total = 0;
int s = 0;
// Iterate with right pointer i
for (int i = 0; i < arr.length; i++) {
// Shrink the window from the left until the
// condition holds
while (arr[i] - arr[s] >= k) {
s++;
}
// All elements between 's' and 'i-1' form
// a valid pair with 'arr[i]'
total += (i - s);
}
return total;
}
public static void main(String[] args)
{
int[] arr = { 1, 10, 4, 2 };
int k = 3;
GFG ob = new GFG();
System.out.println(ob.countPairs(arr, k));
}
}
def countPairs(arr, k):
# Sort the array in non-decreasing order
arr.sort()
total = 0
s = 0
# Iterate with right pointer i
for i in range(len(arr)):
# Shrink the window from the left until the condition holds
while arr[i] - arr[s] >= k:
s += 1
# All elements between 's' and 'i-1' form
# a valid pair with 'arr[i]'
total += (i - s)
return total
if __name__ == "__main__":
arr = [1, 10, 4, 2]
k = 3
print(countPairs(arr, k))
using System;
class GFG {
public int countPairs(int[] arr, int k)
{
// Sort the array in non-decreasing order
Array.Sort(arr);
int total = 0;
int s = 0;
// Iterate with right pointer i
for (int i = 0; i < arr.Length; i++) {
// Shrink the window from the left until the
// condition holds
while (arr[i] - arr[s] >= k) {
s++;
}
// All elements between 's' and 'i-1' form
// a valid pair with 'arr[i]'
total += (i - s);
}
return total;
}
public static void Main()
{
int[] arr = { 1, 10, 4, 2 };
int k = 3;
GFG ob = new GFG();
Console.WriteLine(ob.countPairs(arr, k));
}
}
function countPairs(arr, k)
{
// Sort the array in non-decreasing order
arr.sort((a, b) => a - b);
let total = 0;
let s = 0;
// Iterate with right pointer i
for (let i = 0; i < arr.length; i++) {
// Shrink the window from the left until the
// condition holds
while (arr[i] - arr[s] >= k) {
s++;
}
// All elements between 's' and 'i-1' form
// a valid pair with 'arr[i]'
total += (i - s);
}
return total;
}
// Driver Code
let arr = [ 1, 10, 4, 2 ];
let k = 3;
console.log(countPairs(arr, k));
Output
2