📌  相关文章
📜  使用更新计算数组的按位或的查询

📅  最后修改于: 2021-09-03 03:18:05             🧑  作者: Mango

给定一个由N 个正整数组成的数组arr[]和一个由{i, val}形式的查询组成的二维数组Q[][] ,每个查询的任务是用val替换arr[i]并计算按位OR 修改后的数组。

例子:

朴素的方法:解决问题的最简单的方法是在将arr[Q[i][0]] 更新Q[i][1]后,对每个i查询遍历数组arr[ ]以计算数组的按位或.

时间复杂度: O(N * sizeof(Q))
辅助空间: O(1)

有效方法:按照以下步骤解决问题:

  • 初始化大小为 32 的数组result[] 。将其所有元素设置为 0。
  • 遍历数组arr[]。
    • 迭代每个数组元素的位。
    • 为当前数组元素中找到的每个j个未设置位增加result[j]
  • 现在,遍历数组Q[][]并执行以下操作:
    • 通过从它们各自的位置移除Q[i][0]的设置位来修改result[]
    • 通过从它们各自的位置添加Q[i][0]的设置位来更新result[]
    • result[]数组转换为其等效的十进制值并打印出来。

下面是上述方法的实现:

C++
// C++ implementation of the approach
#include 
using namespace std;
#define bitsSize 32
 
// Function to convert a binary array
// to equivalent decimal representation
int toDecimal(int result[], int size)
{
    // Stores the decimal result
    int ans = 0;
 
    // Traverse the array
    for (int i = 0; i < size; i++) {
        // If non-zero element
        // is encountered
        if (result[i] != 0)
            ans += pow(2, i);
    }
 
    return ans;
}
 
// Function to replace an array
// element old_value by new_value
void findOrUtil(int result[],
                int old_value,
                int new_value)
{
    int i = 0;
 
    // Removing old value from result
    while (old_value != 0) {
        result[i] -= old_value % 2;
        old_value = old_value / 2;
        i++;
    }
 
    i = 0;
 
    // Adding new value to result
    while (new_value != 0) {
        result[i] += new_value % 2;
        new_value = new_value / 2;
        i++;
    }
}
 
// Function to calculate and print
// Bitwise OR of array for each query
void findOR(vector arr,
            vector > queries)
{
    int result[bitsSize];
 
    // Initialize all bits to zero
    memset(result, 0, sizeof(result));
 
    // Precompute and fill result[]
    for (int i = 0; i < arr.size(); i++) {
        int val = arr[i];
        int j = 0;
 
        // Add all set bits to result[]
        while (val != 0) {
            result[j] += val % 2;
            val = val / 2;
            j++;
        }
    }
 
    // Traverse the queries
    for (int q = 0; q < queries.size(); q++) {
        int index = queries[q].first;
        int new_value = queries[q].second;
 
        // Update result[] by replacing
        // arr[index] by new_value
        findOrUtil(result, arr[index], new_value);
 
        // Modify arr[]
        arr[index] = new_value;
 
        // Calculate Bitwise OR
        int ans = toDecimal(result, bitsSize);
 
        // Print the value of Bitwise OR
        cout << ans << endl;
    }
}
 
// Driver Code
int main()
{
 
    // Given array
    vector arr = { 1, 2, 3, 4 };
 
    // Queries of the form {i, value}
    vector > queries;
 
    // 0-indexed queries
    queries.push_back({ 3, 0 });
    queries.push_back({ 1, 8 });
 
    findOR(arr, queries);
 
    return 0;
}


Java
// Java implementation of the approach
import java.util.ArrayList;
 
class GFG{
     
static int bitsSize = 32;
 
static class Pair{
     
    int first;
    int second;
     
    Pair(int first, int second)
    {
        this.first = first;
        this.second = second;
    }
}
 
// Function to convert a binary array
// to equivalent decimal representation
static int toDecimal(int result[], int size)
{
     
    // Stores the decimal result
    int ans = 0;
 
    // Traverse the array
    for(int i = 0; i < size; i++)
    {
         
        // If non-zero element
        // is encountered
        if (result[i] != 0)
            ans += Math.pow(2, i);
    }
    return ans;
}
 
// Function to replace an array
// element old_value by new_value
static void findOrUtil(int result[],
                       int old_value,
                       int new_value)
{
    int i = 0;
 
    // Removing old value from result
    while (old_value != 0)
    {
        result[i] -= old_value % 2;
        old_value = old_value / 2;
        i++;
    }
 
    i = 0;
 
    // Adding new value to result
    while (new_value != 0)
    {
        result[i] += new_value % 2;
        new_value = new_value / 2;
        i++;
    }
}
 
// Function to calculate and print
// Bitwise OR of array for each query
static void findOR(int[] arr, ArrayList queries)
{
    int result[] = new int[bitsSize];
 
    // Precompute and fill result[]
    for(int i = 0; i < arr.length; i++)
    {
        int val = arr[i];
        int j = 0;
 
        // Add all set bits to result[]
        while (val != 0)
        {
            result[j] += val % 2;
            val = val / 2;
            j++;
        }
    }
 
    // Traverse the queries
    for(int q = 0; q < queries.size(); q++)
    {
        int index = queries.get(q).first;
        int new_value = queries.get(q).second;
 
        // Update result[] by replacing
        // arr[index] by new_value
        findOrUtil(result, arr[index], new_value);
 
        // Modify arr[]
        arr[index] = new_value;
 
        // Calculate Bitwise OR
        int ans = toDecimal(result, bitsSize);
 
        // Print the value of Bitwise OR
        System.out.println(ans);
    }
}
 
// Driver code
public static void main(String[] args)
{
 
    // Given array
    int arr[] = { 1, 2, 3, 4 };
 
    // Queries of the form {i, value}
    ArrayList queries = new ArrayList<>();
 
    // 0-indexed queries
    queries.add(new Pair(3, 0));
    queries.add(new Pair(1, 8));
 
    findOR(arr, queries);
}
}
 
// This code is contributed by abhinavjain194


Python3
# Python3 implementation of the approach
 
# Function to convert a binary array
# to equivalent decimal representation
def toDecimal(result, size):
     
    # Stores the decimal result
    ans = 0
 
    # Traverse the array
    for i in range(size):
         
        # If non-zero element
        # is encountered
        if (result[i] != 0):
            ans += pow(2, i)
 
    return ans
 
# Function to replace an array
# element old_value by new_value
def findOrUtil(result, old_value, new_value):
     
    i = 0
 
    # Removing old value from result
    while (old_value != 0):
        result[i] -= old_value % 2
        old_value = old_value // 2
        i += 1
 
    i = 0
 
    # Adding new value to result
    while (new_value != 0):
        result[i] += new_value % 2
        new_value = new_value // 2
        i += 1
 
# Function to calculate and print
# Bitwise OR of array for each query
def findOR(arr, queries):
     
    result = [0] * 32
 
    # Initialize all bits to zero
    # memset(result, 0, sizeof(result))
 
    # Precompute and fill result[]
    for i in range(len(arr)):
        val = arr[i]
        j = 0
 
        # Add all set bits to result[]
        while (val != 0):
            result[j] += val % 2
            val = val // 2
            j += 1
 
    # Traverse the queries
    for q in range(len(queries)):
        index = queries[q][0]
        new_value = queries[q][1]
 
        # Update result[] by replacing
        # arr[index] by new_value
        findOrUtil(result, arr[index],
                   new_value)
 
        # Modify arr[]
        arr[index] = new_value
 
        # Calculate Bitwise OR
        ans = toDecimal(result, 32)
 
        # Print the value of Bitwise OR
        print (ans)
 
# Driver Code
if __name__ == '__main__':
     
    # Given array
    arr = [ 1, 2, 3, 4 ]
 
    # Queries of the form {i, value}
    queries = []
 
    # 0-indexed queries
    queries.append([3, 0])
    queries.append([1, 8])
 
    findOR(arr, queries)
 
# This code is contributed by mohit kumar 29


C#
// C# implementation of the approach
using System;
using System.Collections.Generic;
 
class GFG{
     
static int bitsSize = 32;
 
class Pair{
     
    public int first;
    public int second;
     
    public Pair(int first, int second)
    {
        this.first = first;
        this.second = second;
    }
}
 
// Function to convert a binary array
// to equivalent decimal representation
static int toDecimal(int []result, int size)
{
     
    // Stores the decimal result
    int ans = 0;
 
    // Traverse the array
    for(int i = 0; i < size; i++)
    {
         
        // If non-zero element
        // is encountered
        if (result[i] != 0)
            ans += (int)Math.Pow(2, i);
    }
    return ans;
}
 
// Function to replace an array
// element old_value by new_value
static void findOrUtil(int []result,
                       int old_value,
                       int new_value)
{
    int i = 0;
 
    // Removing old value from result
    while (old_value != 0)
    {
        result[i] -= old_value % 2;
        old_value = old_value / 2;
        i++;
    }
    i = 0;
 
    // Adding new value to result
    while (new_value != 0)
    {
        result[i] += new_value % 2;
        new_value = new_value / 2;
        i++;
    }
}
 
// Function to calculate and print
// Bitwise OR of array for each query
static void findOR(int[] arr, List queries)
{
    int []result = new int[bitsSize];
 
    // Precompute and fill result[]
    for(int i = 0; i < arr.Length; i++)
    {
        int val = arr[i];
        int j = 0;
 
        // Add all set bits to result[]
        while (val != 0)
        {
            result[j] += val % 2;
            val = val / 2;
            j++;
        }
    }
 
    // Traverse the queries
    for(int q = 0; q < queries.Count; q++)
    {
        int index = queries[q].first;
        int new_value = queries[q].second;
 
        // Update result[] by replacing
        // arr[index] by new_value
        findOrUtil(result, arr[index], new_value);
 
        // Modify []arr
        arr[index] = new_value;
 
        // Calculate Bitwise OR
        int ans = toDecimal(result, bitsSize);
 
        // Print the value of Bitwise OR
        Console.WriteLine(ans);
    }
}
 
// Driver code
public static void Main(String[] args)
{
 
    // Given array
    int []arr = { 1, 2, 3, 4 };
 
    // Queries of the form {i, value}
    List queries = new List();
 
    // 0-indexed queries
    queries.Add(new Pair(3, 0));
    queries.Add(new Pair(1, 8));
 
    findOR(arr, queries);
}
}
 
// This code is contributed by 29AjayKumar


Javascript


输出:
3
11

时间复杂度:O(N)
辅助空间: O(1)

如果您想与行业专家一起参加直播课程,请参阅Geeks Classes Live