Minimum bitwise OR after removing at most K elements from given Array
Last Updated :
03 May, 2023
Given an array A[] of length N, the task is to find the minimum possible value of bitwise OR of the elements after removing at most K elements.
Examples:
Input: A = {1, 10, 9, 4, 5, 16, 8}, K = 3
Output: 11
Explanation: Remove 4, 5, 16 for the given array.
The remaining elements are {1, 10, 9, 5}.
The OR of these elements are 11 which is the minimum possible.
Input: A = {1, 2, 4, 8}, K = 1
Output: 7
Explanation: Remove 8 from the Array, Minimum OR= 1 | 2 | 4 = 7
Approach: This problem can be solved using bit manipulation on the basis of the following idea:
Try to remove the highest MSB elements first, then the elements having 2nd highest MSB and so on until K elements are removed.
Follow the illustration given below for a better understanding.
Illustration :
Consider A[] = [1, 10, 9, 4, 5, 16, 8 ]
- Binary representation of the elements are:
1 – 00001
10 – 01010
9 – 01001
4 – 00100
5 – 00101
16 – 10000
8 – 01000
- The positions of the MSB of every elements are:
1 -> 0, 10 -> 3, 9 -> 3, 4 -> 2, 5 -> 2, 16 -> 4, 8 -> 3
- Therefore count of elements having MSB at ith position are as given below:
setBitCount = [1, 0, 2, 3, 1 ]
MSB position 0, 1, 2, 3, 4
- Traverse array and check if current setBitCount is less than k, then remove all elements with current Bit as FirstSetBit.
For, K = 3, traverse array:
=>When i = 4: setBitCount[i] = 1, which is less than K so remove 16, and now K = 2.
=>When i = 3: K < setBitCount[i] (i.e 3). So don’t remove it.
=>When i = 2: setBitCount[i] = 2 ≤ K, so remove 4 and 5. Now, K =0.
- Calculate OR for all remaining elements i.e (1, 5, 9, 10) = 11
Follow the steps mentioned below to implement the above observation:
- Create a hash array.
- Traverse the given array and increment the MSB Index of every element into the hash array.
- Now, traverse the hash array from MSB and in each iteration:
- Check if it is possible to remove all elements having the ith bit as MSB i.e. setBitCount ≤ K.
- If setBitCount ≤ K, don’t calculate OR for that elements and, just decrease the K.
- if not, calculate the OR for elements with ith bit as MSB.
- Return Calculate OR after removing K elements.
Below is the implementation of the above approach:
C++
#include <bits/stdc++.h>
using namespace std;
int minimumOR(vector< int > A, int N, int K)
{
vector< int > SetBitCount(32, 0);
int OR = 0, FirstSetBit = 0;
sort(A.rbegin(), A.rend());
for ( int i = 0; i < N; i++) {
FirstSetBit = log2(A[i]) + 1;
SetBitCount[FirstSetBit]++;
}
for ( int i = 31, j = 0; i >= 0; i--) {
if (SetBitCount[i] <= K) {
K -= SetBitCount[i];
j += SetBitCount[i];
}
else {
for ( int x = j;
j < x + SetBitCount[i]; j++)
OR = OR | A[j];
}
}
return OR;
}
int main()
{
int N = 7;
vector< int > A = { 1, 10, 9, 4, 5, 16, 8 };
int K = 3;
cout << minimumOR(A, N, K);
return 0;
}
|
Java
import java.util.*;
public class GFG
{
static void reverse( int a[], int n)
{
int i, k, t;
for (i = 0 ; i < n / 2 ; i++) {
t = a[i];
a[i] = a[n - i - 1 ];
a[n - i - 1 ] = t;
}
}
static int minimumOR( int [] A, int N, int K)
{
int [] SetBitCount = new int [ 32 ];
for ( int i = 0 ; i < 32 ; i++) {
SetBitCount[i] = 0 ;
}
int OR = 0 , FirstSetBit = 0 ;
Arrays.sort(A);
reverse(A, N);
for ( int i = 0 ; i < N; i++) {
FirstSetBit
= ( int )(Math.log(A[i]) / Math.log( 2 )) + 1 ;
SetBitCount[FirstSetBit]++;
}
for ( int i = 31 , j = 0 ; i >= 0 ; i--) {
if (SetBitCount[i] <= K) {
K -= SetBitCount[i];
j += SetBitCount[i];
}
else {
for ( int x = j; j < x + SetBitCount[i]; j++)
OR = (OR | A[j]);
}
}
return OR;
}
public static void main(String args[])
{
int N = 7 ;
int [] A = { 1 , 10 , 9 , 4 , 5 , 16 , 8 };
int K = 3 ;
System.out.println(minimumOR(A, N, K));
}
}
|
Python
import math
def minimumOR(A, N, K):
SetBitCount = [ 0 ] * 32
OR = 0
FirstSetBit = 0
A.sort(reverse = True )
for i in range ( 0 , N):
FirstSetBit = int (math.log(A[i], 2 )) + 1
SetBitCount[FirstSetBit] + = 1
j = 0
i = 31
while (i > = 0 ):
if (SetBitCount[i] < = K):
K - = SetBitCount[i]
j + = SetBitCount[i]
else :
x = j
while (j < x + SetBitCount[i]):
OR = OR | A[j]
j + = 1
i - = 1
return OR
N = 7
A = [ 1 , 10 , 9 , 4 , 5 , 16 , 8 ]
K = 3
print (minimumOR(A, N, K))
|
C#
using System;
class GFG {
static int minimumOR( int [] A, int N, int K)
{
int [] SetBitCount = new int [32];
for ( int i = 0; i < 32; i++) {
SetBitCount[i] = 0;
}
int OR = 0, FirstSetBit = 0;
Array.Sort(A);
Array.Reverse(A);
for ( int i = 0; i < N; i++) {
FirstSetBit = ( int )Math.Log(A[i], 2) + 1;
SetBitCount[FirstSetBit]++;
}
for ( int i = 31, j = 0; i >= 0; i--) {
if (SetBitCount[i] <= K) {
K -= SetBitCount[i];
j += SetBitCount[i];
}
else {
for ( int x = j; j < x + SetBitCount[i]; j++)
OR = (OR | A[j]);
}
}
return OR;
}
public static void Main()
{
int N = 7;
int [] A = { 1, 10, 9, 4, 5, 16, 8 };
int K = 3;
Console.Write(minimumOR(A, N, K));
}
}
|
Javascript
<script>
function minimumOR(A, N, K) {
let SetBitCount = new Array(32).fill(0);
let OR = 0, FirstSetBit = 0;
A.sort( function (a, b) { return b - a })
for (let i = 0; i < N; i++) {
FirstSetBit = Math.log2(A[i]) + 1;
SetBitCount[FirstSetBit]++;
}
for (let i = 31, j = 0; i >= 0; i--) {
if (SetBitCount[i] <= K) {
K -= SetBitCount[i];
j += SetBitCount[i];
}
else {
for (let x = j;
j < x + SetBitCount[i]; j++)
OR = OR | A[j];
}
}
return OR;
}
let N = 7;
let A = [1, 10, 9, 4, 5, 16, 8]
let K = 3;
document.write(minimumOR(A, N, K));
</script>
|
Time Complexity: O(N* log(N))
Auxiliary Space: O(N)
Like Article
Suggest improvement
Share your thoughts in the comments
Please Login to comment...