求 K 大小子数组的按位与和按位或的最大乘积
给定一个包含N个整数和一个整数K的数组arr[] ,任务是找到K大小子数组的所有元素的按位与和按位或的乘积的最大值。
例子:
Input: arr[] = {1, 2, 3, 4}, K = 2
Output: 6
Explanation: Bitwise AND and Bitwise XOR of all K-sized subarrays is {(0, 3), (2, 3), (0, 7)} respectively. Therefore the maximum possible value of their product is 2 * 3 = 6 which is the required answer.
Input: arr[] = {6, 7, 7, 10, 8, 2}, K = 3
Output: 42
方法:给定的问题可以使用滑动窗口技术来解决。这个想法是为 K 大小的子数组窗口维护按位与和按位或的值,这可以通过维护一个数组来完成,该数组存储当前窗口所有元素的每个位的计数。如果第i个计数 位是K ,该位必须包含在按位与中,如果位的计数大于1 ,则必须包含在按位或中。将其乘积在所有窗口中的最大值存储在变量ans中,这是所需的答案。
下面是上述方法的实现:
C++
// C++ program for the above approach
#include
using namespace std;
// Function to convert bit array to
// decimal number representing OR
int build_or(int bit[])
{
int ans = 0;
for (int i = 0; i < 32; i++)
if (bit[i])
ans += (1 << i);
return ans;
}
// Function to convert bit array to
// decimal number representing AND
int build_and(int bit[], int k)
{
int ans = 0;
for (int i = 0; i < 32; i++)
if (bit[i] == k)
ans += (1 << i);
return ans;
}
// Function to find maximum value of
// AND * OR over all K sized subarrays
int maximizeAndOr(int arr[], int N, int K)
{
// Maintain an integer array bit[]
// of size 32 all initialized to 0
int bit[32] = { 0 };
// Create a sliding window of size k
for (int i = 0; i < K; i++) {
for (int j = 0; j < 32; j++) {
if (arr[i] & (1 << j))
bit[j]++;
}
}
int ans = build_and(bit, K) * build_or(bit);
for (int i = K; i < N; i++) {
// Perform operation for
// removed element
for (int j = 0; j < 32; j++) {
if (arr[i - K] & (1 << j))
bit[j]--;
}
// Perform operation for
// added_element
for (int j = 0; j < 32; j++) {
if (arr[i] & (1 << j))
bit[j]++;
}
// Taking maximum value
ans = max(ans, build_and(bit, K)
* build_or(bit));
}
return ans;
}
// Driver Code
int main()
{
int arr[] = { 6, 7, 7, 10, 8, 2 };
int N = sizeof(arr) / sizeof(arr[0]);
int K = 3;
cout << maximizeAndOr(arr, N, K);
return 0;
}
Java
// Java program for the above approach
import java.util.*;
class GFG{
// Function to convert bit array to
// decimal number representing OR
static int build_or(int[] bit)
{
int ans = 0;
for(int i = 0; i < 32; i++)
if (bit[i] > 0)
ans += (1 << i);
return ans;
}
// Function to convert bit array to
// decimal number representing AND
static int build_and(int[] bit, int k)
{
int ans = 0;
for(int i = 0; i < 32; i++)
if (bit[i] == k)
ans += (1 << i);
return ans;
}
// Function to find maximum value of
// AND * OR over all K sized subarrays
static int maximizeAndOr(int[] arr, int N, int K)
{
// Maintain an integer array bit[]
// of size 32 all initialized to 0
int[] bit = new int[32];
// Create a sliding window of size k
for(int i = 0; i < K; i++)
{
for(int j = 0; j < 32; j++)
{
if ((arr[i] & (1 << j)) > 0)
bit[j]++;
}
}
int ans = build_and(bit, K) * build_or(bit);
for(int i = K; i < N; i++)
{
// Perform operation for
// removed element
for(int j = 0; j < 32; j++)
{
if ((arr[i - K] & (1 << j)) > 0)
bit[j]--;
}
// Perform operation for
// added_element
for(int j = 0; j < 32; j++)
{
if ((arr[i] & (1 << j)) > 0)
bit[j]++;
}
// Taking maximum value
ans = Math.max(ans, build_and(bit, K) *
build_or(bit));
}
return ans;
}
// Driver Code
public static void main(String args[])
{
int[] arr = { 6, 7, 7, 10, 8, 2 };
int N = arr.length;
int K = 3;
System.out.println(maximizeAndOr(arr, N, K));
}
}
// This code is contributed by Samim Hossain Mondal.
Python3
# Python3 program for the above approach
# Function to convert bit array to
# decimal number representing OR
def build_or(bit):
ans = 0
for i in range(0, 32):
if (bit[i]):
ans += (1 << i)
return ans
# Function to convert bit array to
# decimal number representing AND
def build_and(bit, k):
ans = 0
for i in range(0, 32):
if (bit[i] == k):
ans += (1 << i)
return ans
# Function to find maximum value of
# AND * OR over all K sized subarrays
def maximizeAndOr(arr, N, K):
# Maintain an integer array bit[]
# of size 32 all initialized to 0
bit = [0 for _ in range(32)]
# Create a sliding window of size k
for i in range(0, K):
for j in range(0, 32):
if (arr[i] & (1 << j)):
bit[j] += 1
ans = build_and(bit, K) * build_or(bit)
for i in range(K, N):
# Perform operation for
# removed element
for j in range(0, 32):
if (arr[i - K] & (1 << j)):
bit[j] -= 1
# Perform operation for
# added_element
for j in range(0, 32):
if (arr[i] & (1 << j)):
bit[j] += 1
# Taking maximum value
ans = max(ans, build_and(bit, K) *
build_or(bit))
return ans
# Driver Code
if __name__ == "__main__":
arr = [ 6, 7, 7, 10, 8, 2 ]
N = len(arr)
K = 3
print(maximizeAndOr(arr, N, K))
# This code is contributed by rakeshsahni
C#
// C# program for the above approach
using System;
class GFG
{
// Function to convert bit array to
// decimal number representing OR
static int build_or(int[] bit)
{
int ans = 0;
for (int i = 0; i < 32; i++)
if (bit[i] > 0)
ans += (1 << i);
return ans;
}
// Function to convert bit array to
// decimal number representing AND
static int build_and(int[] bit, int k)
{
int ans = 0;
for (int i = 0; i < 32; i++)
if (bit[i] == k)
ans += (1 << i);
return ans;
}
// Function to find maximum value of
// AND * OR over all K sized subarrays
static int maximizeAndOr(int[] arr, int N, int K)
{
// Maintain an integer array bit[]
// of size 32 all initialized to 0
int[] bit = new int[32];
// Create a sliding window of size k
for (int i = 0; i < K; i++) {
for (int j = 0; j < 32; j++) {
if ((arr[i] & (1 << j)) > 0)
bit[j]++;
}
}
int ans = build_and(bit, K) * build_or(bit);
for (int i = K; i < N; i++) {
// Perform operation for
// removed element
for (int j = 0; j < 32; j++) {
if ((arr[i - K] & (1 << j)) > 0)
bit[j]--;
}
// Perform operation for
// added_element
for (int j = 0; j < 32; j++) {
if ((arr[i] & (1 << j)) > 0)
bit[j]++;
}
// Taking maximum value
ans = Math.Max(ans, build_and(bit, K)
* build_or(bit));
}
return ans;
}
// Driver Code
public static void Main()
{
int[] arr = { 6, 7, 7, 10, 8, 2 };
int N = arr.Length;
int K = 3;
Console.WriteLine(maximizeAndOr(arr, N, K));
}
}
// This code is contributed by ukasp.
Javascript
输出
42
时间复杂度:O(N*log N)
辅助空间: O(1)