Given Array of size n and a number k, find all elements that appear more than n/k times
Last Updated :
18 Apr, 2023
Given an array of size n and an integer k, find all elements in the array that appear more than n/k times.
Examples:
Input: arr[] = {3, 1, 2, 2, 1, 2, 3, 3}, k = 4
Output: {2, 3}
Explanation: Here n/k is 8/4 = 2, therefore 2 appears 3 times in the array that is greater than 2 and 3 appears 3 times in the array that is greater than 2
Input: arr[] = {9, 8, 7, 9, 2, 9, 7}, k = 3
Output: {9}
Explanation: Here n/k is 7/3 = 2, therefore 9 appears 3 times in the array that is greater than 2.
Find all elements that appear more than n/k times using Hashing:
The idea is to pick all elements one by one. For every picked element, count its occurrences by traversing the array, if count becomes more than n/k, then print the element.
Follow the steps below to solve the problem:
- First, make a frequency map of all the elements in the array
- Then traverse the map and check the frequency of every element
- If the frequency is greater than n/k then print the element.
Below is the implementation of the above approach:
C++
#include <bits/stdc++.h>
using namespace std;
void morethanNbyK( int arr[], int n, int k)
{
int x = n / k;
unordered_map< int , int > freq;
for ( int i = 0; i < n; i++) {
freq[arr[i]]++;
}
for ( auto i : freq) {
if (i.second > x) {
cout << i.first << endl;
}
}
}
int main()
{
int arr[] = { 1, 1, 2, 2, 3, 5, 4, 2, 2, 3, 1, 1, 1 };
int n = sizeof (arr) / sizeof (arr[0]);
int k = 4;
morethanNbyK(arr, n, k);
return 0;
}
|
Java
import java.util.*;
public class Main
{
public static void morethanNdK( int a[], int n, int k)
{
int x = n / k;
HashMap<Integer, Integer> y = new HashMap<>();
for ( int i = 0 ; i < n; i++) {
if (!y.containsKey(a[i]))
y.put(a[i], 1 );
else {
int count = y.get(a[i]);
y.put(a[i], count + 1 );
}
}
for (Map.Entry m : y.entrySet()) {
Integer temp = (Integer)m.getValue();
if (temp > x)
System.out.println(m.getKey());
}
}
public static void main(String[] args)
{
int a[] = new int [] { 1 , 1 , 2 , 2 , 3 , 5 , 4 ,
2 , 2 , 3 , 1 , 1 , 1 };
int n = 12 ;
int k = 4 ;
morethanNdK(a, n, k);
}
}
|
Python3
def morethanNbyK(arr, n, k):
x = n / / k
freq = {}
for i in range (n):
if arr[i] in freq:
freq[arr[i]] + = 1
else :
freq[arr[i]] = 1
for i in freq:
if (freq[i] > x):
print (i)
if __name__ = = '__main__' :
arr = [ 1 , 1 , 2 , 2 , 3 , 5 , 4 , 2 , 2 , 3 , 1 , 1 , 1 ]
n = len (arr)
k = 4
morethanNbyK(arr, n, k)
|
C#
using System;
using System.Collections.Generic;
class GFG {
public static void morethanNdK( int [] a, int n, int k)
{
int x = n / k;
Dictionary< int , int > y = new Dictionary< int , int >();
for ( int i = 0; i < n; i++) {
if (!y.ContainsKey(a[i]))
y.Add(a[i], 1);
else {
int count = y[a[i]];
y[a[i]] = count + 1;
}
}
foreach (KeyValuePair< int , int > m in y)
{
int temp = ( int )m.Value;
if (temp > x)
Console.WriteLine(m.Key);
}
}
public static void Main(String[] args)
{
int [] a = new int [] { 1, 1, 2, 2, 3, 5, 4,
2, 2, 3, 1, 1, 1 };
int n = 12;
int k = 4;
morethanNdK(a, n, k);
}
}
|
Javascript
<script>
function morethanNdK(a,n,k)
{
let x = n / k;
let y= new Map();
for (let i = 0; i < n; i++)
{
if (!y.has(a[i]))
y.set(a[i], 1);
else
{
let count = y.get(a[i]);
y.set(a[i], count + 1);
}
}
for (let [key, value] of y.entries())
{
let temp = value;
if (temp > x)
document.write(key+ "<br>" );
}
}
let a=[1, 1, 2, 2, 3, 5, 4,
2, 2, 3, 1, 1, 1];
let n = 12;
let k = 4;
morethanNdK(a, n, k);
</script>
|
Time Complexity: O(N), Traversing the array of size N.
Auxiliary Space: O(N), Space occupied by the hashmap
Find all elements that appear more than n/k times using Moore’s Voting Algorithm:
The idea is to apply Moore’s Voting algorithm, as there can be at max k – 1 elements present in the array which appears more than n/k times so their will be k – 1 candidates. When we encounter an element which is one of our candidates then increment the count else decrement the count.
Illustration:
Consider k = 4, n = 9
Given array: 3 1 2 2 2 1 4 3 3
i = 0
temp[] has one element {3} with count 1
i = 1
temp[] has two elements {3, 1} with counts 1 and 1 respectively
i = 2
temp[] has three elements, {3, 1, 2} with counts as 1, 1 and 1 respectively.
i = 3
temp[] has three elements, {3, 1, 2} with counts as 1, 1 and 2 respectively.
i = 4
temp[] has three elements, {3, 1, 2} with counts as 1, 1 and 3 respectively.
i = 5
temp[] has three elements, {3, 1, 2 with counts as 1, 2 and 3 respectively.
i = 6
temp[] has two elements, {1, 2} with counts as 1 and 2 respectively.
i = 7
temp[] has three elements, {3, 1, 2} with counts as 1, 1 and 2 respectively.
i = 8
temp[] has three elements, {3, 1, 2} with counts as 2, 1 and 2 respectively.
Follow the steps below to solve the problem:
- Create a temporary array of size (k – 1) to store elements and their counts (The output elements are going to be among these k-1 elements).
- Traverse through the input array and update temp[] (add/remove an element or increase/decrease count) for every traversed element. The array temp[] stores potential (k-1) candidates at every step.
- Iterate through final (k-1) potential candidates (stored in temp[]). or every element, check if it actually has counted of more than n/k.
Below is the implementation of the above approach.
C++
#include <iostream>
using namespace std;
struct eleCount {
int e;
int c;
};
void moreThanNdK( int arr[], int n, int k)
{
if (k < 2)
return ;
struct eleCount temp[k - 1];
for ( int i = 0; i < k - 1; i++)
temp[i].c = 0;
for ( int i = 0; i < n; i++) {
int j;
for (j = 0; j < k - 1; j++) {
if (temp[j].e == arr[i]) {
temp[j].c += 1;
break ;
}
}
if (j == k - 1) {
int l;
for (l = 0; l < k - 1; l++) {
if (temp[l].c == 0) {
temp[l].e = arr[i];
temp[l].c = 1;
break ;
}
}
if (l == k - 1)
for (l = 0; l < k - 1; l++)
temp[l].c -= 1;
}
}
for ( int i = 0; i < k - 1; i++) {
int ac = 0;
for ( int j = 0; j < n; j++)
if (arr[j] == temp[i].e)
ac++;
if (ac > n / k)
cout << "Number:" << temp[i].e
<< " Count:" << ac << endl;
}
}
int main()
{
int arr1[] = { 4, 5, 6, 7, 8, 4, 4 };
int size = sizeof (arr1) / sizeof (arr1[0]);
int k = 3;
moreThanNdK(arr1, size, k);
return 0;
}
|
Java
import java.util.*;
class GFG {
static class eleCount {
int e;
int c;
};
static void moreThanNdK( int arr[], int n, int k)
{
if (k < 2 )
return ;
eleCount[] temp = new eleCount[k - 1 ];
for ( int i = 0 ; i < k - 1 ; i++)
temp[i] = new eleCount();
for ( int i = 0 ; i < k - 1 ; i++) {
temp[i].c = 0 ;
}
for ( int i = 0 ; i < n; i++) {
int j;
for (j = 0 ; j < k - 1 ; j++) {
if (temp[j].e == arr[i]) {
temp[j].c += 1 ;
break ;
}
}
if (j == k - 1 ) {
int l;
for (l = 0 ; l < k - 1 ; l++) {
if (temp[l].c == 0 ) {
temp[l].e = arr[i];
temp[l].c = 1 ;
break ;
}
}
if (l == k - 1 )
for (l = 0 ; l < k - 1 ; l++)
temp[l].c -= 1 ;
}
}
for ( int i = 0 ; i < k - 1 ; i++) {
int ac = 0 ;
for ( int j = 0 ; j < n; j++)
if (arr[j] == temp[i].e)
ac++;
if (ac > n / k)
System.out.print( "Number:" + temp[i].e
+ " Count:" + ac + "\n" );
}
}
public static void main(String[] args)
{
int arr1[] = { 4 , 5 , 6 , 7 , 8 , 4 , 4 };
int size = arr1.length;
int k = 3 ;
moreThanNdK(arr1, size, k);
}
}
|
Python3
def moreThanNdK(arr, n, k):
if (k < 2 ):
return
temp = [[ 0 for i in range ( 2 )]
for i in range (k)]
for i in range (k - 1 ):
temp[i][ 0 ] = 0
for i in range (n):
j = 0
while j < k - 1 :
if (temp[j][ 1 ] = = arr[i]):
temp[j][ 0 ] + = 1
break
j + = 1
if (j = = k - 1 ):
l = 0
while l < k - 1 :
if (temp[l][ 0 ] = = 0 ):
temp[l][ 1 ] = arr[i]
temp[l][ 0 ] = 1
break
l + = 1
if (l = = k - 1 ):
while l < k:
temp[l][ 0 ] - = 1
l + = 1
for i in range (k - 1 ):
ac = 0
for j in range (n):
if (arr[j] = = temp[i][ 1 ]):
ac + = 1
if (ac > n / / k):
print ( "Number:" ,
temp[i][ 1 ],
" Count:" , ac)
if __name__ = = '__main__' :
arr1 = [ 4 , 5 , 6 , 7 , 8 , 4 , 4 ]
size = len (arr1)
k = 3
moreThanNdK(arr1, size, k)
|
C#
using System;
class GFG {
public class eleCount {
public int e;
public int c;
};
static void moreThanNdK( int [] arr, int n, int k)
{
if (k < 2)
return ;
eleCount[] temp = new eleCount[k - 1];
for ( int i = 0; i < k - 1; i++)
temp[i] = new eleCount();
for ( int i = 0; i < k - 1; i++) {
temp[i].c = 0;
}
for ( int i = 0; i < n; i++) {
int j;
for (j = 0; j < k - 1; j++) {
if (temp[j].e == arr[i]) {
temp[j].c += 1;
break ;
}
}
if (j == k - 1) {
int l;
for (l = 0; l < k - 1; l++) {
if (temp[l].c == 0) {
temp[l].e = arr[i];
temp[l].c = 1;
break ;
}
}
if (l == k - 1)
for (l = 0; l < k - 1; l++)
temp[l].c -= 1;
}
}
for ( int i = 0; i < k - 1; i++) {
int ac = 0;
for ( int j = 0; j < n; j++)
if (arr[j] == temp[i].e)
ac++;
if (ac > n / k)
Console.Write( "Number:" + temp[i].e
+ " Count:" + ac + "\n" );
}
}
public static void Main(String[] args)
{
int [] arr1 = { 4, 5, 6, 7, 8, 4, 4 };
int size = arr1.Length;
int k = 3;
moreThanNdK(arr1, size, k);
}
}
|
Javascript
<script>
function moreThanNdK(arr, n, k){
if (k < 2)
return ;
let temp = new Array(k-1);
for (let i = 0; i < k - 1; i++){
temp[i] = new Array(2);
temp[i][0] = 0;
}
for (let i = 0; i < n; i++){
let j;
for (j = 0; j < k - 1; j++)
{
if (temp[j][1] == arr[i])
{
temp[j][0] += 1;
break ;
}
}
if (j == k - 1){
let l;
for (l = 0; l < k - 1; l++)
{
if (temp[l][0] == 0)
{
temp[l][1] = arr[i];
temp[l][0] = 1;
break ;
}
}
if (l == k - 1)
for (l = 0; l < k-1; l++)
temp[l][0] -= 1;
}
}
for (let i = 0; i < k - 1; i++){
let ac = 0
for (let j = 0; j < n; j++){
if (arr[j] == temp[i][1])
ac++;
}
if (ac > Math.floor(n/k))
document.write( "Number: " + temp[i][1] +
" Count: " + ac, "</br>" )
}
}
document.write( "First Test" , "</br>" )
let arr1 = [4, 5, 6, 7, 8, 4, 4]
let size = arr1.length
let k = 3
moreThanNdK(arr1, size, k)
document.write( "Second Test" , "</br>" )
let arr2 = [4, 2, 2, 7]
size = arr2.length
k = 3
moreThanNdK(arr2, size, k)
document.write( "Third Test" , "</br>" )
let arr3 = [2, 7, 2]
size = arr3.length
k = 2
moreThanNdK(arr3, size, k)
document.write( "Fourth Test" , "</br>" )
let arr4 = [2, 3, 3, 2]
size = arr4.length
k = 3
moreThanNdK(arr4, size, k)
</script>
|
Time Complexity: O(N * K), Checking for each element of the array(size N) in the candidate array of size K
Auxiliary Space: O(K), Space required to store the candidates.
Find all elements that appear more than n/k times using Built-in Python functions:
This approach is same the first approach but here in python there is a counter() that calculates the frequency array.
- Count the frequencies of every element using Counter() function.
- Traverse the frequency array and print all the elements which occur at more than n/k times.
Below is the implementation of the above approach:
Python3
from collections import Counter
def printElements(arr, n, k):
x = n / / k
mp = Counter(arr)
for it in mp:
if mp[it] > x:
print (it)
if __name__ = = '__main__' :
arr = [ 1 , 1 , 2 , 2 , 3 , 5 , 4 , 2 , 2 , 3 , 1 , 1 , 1 ]
n = len (arr)
k = 4
printElements(arr, n, k)
|
Java
import java.io.*;
import java.util.*;
class GFG {
public static void printElements( int [] arr, int n, int k) {
int x = n / k;
HashMap<Integer, Integer> mp = new HashMap<>();
for ( int i : arr) {
if (mp.containsKey(i)) {
mp.put(i, mp.get(i) + 1 );
} else {
mp.put(i, 1 );
}
}
for ( int key : mp.keySet()) {
if (mp.get(key) > x) {
System.out.println(key);
}
}
}
public static void main(String[] args) {
int [] arr = { 1 , 1 , 2 , 2 , 3 , 5 , 4 , 2 , 2 , 3 , 1 , 1 , 1 };
int n = arr.length;
int k = 4 ;
printElements(arr, n, k);
}
}
|
C++
#include <iostream>
#include <unordered_map>
using namespace std;
void printElements( int arr[], int n, int k)
{
int x = n/k;
unordered_map< int , int > mp;
for ( int i = 0; i < n; i++)
mp[arr[i]]++;
for ( auto it : mp)
if (it.second > x)
cout << it.first << endl;
}
int main()
{
int arr[] = { 1, 1, 2, 2, 3, 5, 4, 2, 2, 3, 1, 1, 1 };
int n = sizeof (arr)/ sizeof (arr[0]);
int k = 4;
printElements(arr, n, k);
return 0;
}
|
Javascript
function printElements(arr, n, k){
let x = parseInt(n/k);
let mp = new Map();
for (let ele of arr){
if (ele in mp){
mp[ele] += 1;
}
else {
mp[ele] = 1;
}
}
for (let it in mp){
if (mp[it] > x){
console.log(it);
}
}
}
let arr = [ 1, 1, 2, 2, 3, 5, 4, 2, 2, 3, 1, 1, 1 ];
let n = arr.length;
let k = 4;
printElements(arr, n, k);
|
C#
using System;
using System.Collections.Generic;
class GFG
{
static void Main()
{
int [] arr = { 1, 1, 2, 2, 3, 5, 4, 2, 2, 3, 1, 1, 1 };
int n = arr.Length;
int k = 4;
PrintElements(arr, n, k);
}
static void PrintElements( int [] arr, int n, int k)
{
int x = n / k;
Dictionary< int , int > mp = new Dictionary< int , int >();
for ( int i = 0; i < n; i++)
{
if (mp.ContainsKey(arr[i]))
{
mp[arr[i]]++;
}
else
{
mp[arr[i]] = 1;
}
}
foreach (KeyValuePair< int , int > item in mp)
{
if (item.Value > x)
{
Console.WriteLine(item.Key);
}
}
}
}
|
Time Complexity: O(N), Traversing over the array to store the frequency
Auxiliary Space: O(N), Space used to store the frequency
Please Login to comment...