Given an array **arr[]** consisting of **N** non-negative integers and a 2D array **queries[][]** consisting of queries of the type **{X, M}**, the task for each query is to find the maximum Bitwise XOR of **X** with any array element whose value is at most **M**. If it is not possible to find the Bitwise XOR, then print **“-1”**.

**Examples:**

Input:arr[] = {0, 1, 2, 3, 4}, queries[][] = {{3, 1}, {1, 3}, {5, 6}}Output:{3, 3, 7}Explanation:Query 1:The query is {3, 1}. Maximum Bitwise XOR = 3 ^ 0 = 3.Query 2:The query is {1, 3}. Maximum Bitwise XOR = 1 ^ 2 = 3.Query 3:The query is {5, 6}. Maximum Bitwise XOR = 5 ^ 2 = 7.

Input:arr[] = {5, 2, 4, 6, 6, 3}, queries[][] = {{12, 4}, {8, 1}, {6, 3}}Output:{15, -1, 5}

**Naive Approach:** The simplest approach to solve the given problem is to traverse the given array for each query **{X, M}** and print the maximum value of **Bitwise XOR** of **X** with an array element with a value at most **M**. If there doesn’t exist any value less than **M**, then print **“-1”** for the query.**Time Complexity:** O(N*Q)**Auxiliary Space:** O(1)

**Efficient Approach:** The above approach can also be optimized by using the Trie data structure to store all the elements having values **at most M**. Therefore, the problem reduces to finding the maximum XOR of two elements in an array. Follow the steps below to solve the problem:

- Initialize a variable, say
**index**, to traverse the array. - Initialize an array, say
**ans[]**, that stores the result for each query. - Initialize an auxiliary array, say
**temp[][3]**, and store all the queries in it with the index of each query. - Sort the given array
**temp[]**on the basis of the second parameter, i.e.**temp[1]**(=**M**). - Sort the given array
**arr[]**in ascending order. - Traverse the array
**temp[]**and for each query**{X, M, idx}**, perform the following steps:- Iterate until the value of
**index**is less than**N**and**arr[index]**is at most**M**or not. If found to be true, then insert that node as the binary representation of**N**and increment**index**. - After completing the above steps, if the value of
**index**is**non-zero**, then find the node with value**X**in the Trie(say**result**) and update the maximum value for the current query as**result**. Otherwise, update the maximum value for the current query as**“-1”**.

- Iterate until the value of
- After completing the above steps, print the array
**ans[]**as the resultant maximum values for each query.

Below is the implementation of the above approach:

## Java

`// Java program for the above approach` ` ` `import` `java.io.*;` `import` `java.util.*;` ` ` `// Trie Node Class` `class` `TrieNode {` ` ` `TrieNode nums[] = ` `new` `TrieNode[` `2` `];` ` ` `int` `prefixValue;` `}` ` ` `class` `sol {` ` ` ` ` `// Function to find the maximum XOR` ` ` `// of X with any array element <= M` ` ` `// for each query of the type {X, M}` ` ` `public` `void` `maximizeXor(` ` ` `int` `[] nums, ` `int` `[][] queries)` ` ` `{` ` ` `int` `queriesLength = queries.length;` ` ` `int` `[] ans = ` `new` `int` `[queriesLength];` ` ` `int` `[][] temp = ` `new` `int` `[queriesLength][` `3` `];` ` ` ` ` `// Stores the queries` ` ` `for` `(` `int` `i = ` `0` `; i < queriesLength; i++) {` ` ` `temp[i][` `0` `] = queries[i][` `0` `];` ` ` `temp[i][` `1` `] = queries[i][` `1` `];` ` ` `temp[i][` `2` `] = i;` ` ` `}` ` ` ` ` `// Sort the query` ` ` `Arrays.sort(temp,` ` ` `(a, b) -> {` ` ` `return` `a[` `1` `]` ` ` `- b[` `1` `];` ` ` `});` ` ` `int` `index = ` `0` `;` ` ` ` ` `// Sort the array` ` ` `Arrays.sort(nums);` ` ` `TrieNode root = ` `new` `TrieNode();` ` ` ` ` `// Traverse the given query` ` ` `for` `(` `int` `query[] : temp) {` ` ` ` ` `// Traverse the array nums[]` ` ` `while` `(index < nums.length` ` ` `&& nums[index]` ` ` `<= query[` `1` `]) {` ` ` ` ` `// Insert the node into the Trie` ` ` `insert(root, nums[index]);` ` ` `index++;` ` ` `}` ` ` ` ` `// Stores the resultant` ` ` `// maximum value` ` ` `int` `tempAns = -` `1` `;` ` ` ` ` `// Find the maximum value` ` ` `if` `(index != ` `0` `) {` ` ` ` ` `// Search the node in the Trie` ` ` `tempAns = search(root,` ` ` `query[` `0` `]);` ` ` `}` ` ` ` ` `// Update the result` ` ` `// for each query` ` ` `ans[query[` `2` `]] = tempAns;` ` ` `}` ` ` ` ` `// Print the answer` ` ` `for` `(` `int` `num : ans) {` ` ` `System.out.print(num + ` `" "` `);` ` ` `}` ` ` `}` ` ` ` ` `// Function to insert the` ` ` `// root in the trieNode` ` ` `public` `void` `insert(TrieNode root,` ` ` `int` `n)` ` ` `{` ` ` `TrieNode node = root;` ` ` ` ` `// Iterate from 31 to 0` ` ` `for` `(` `int` `i = ` `31` `; i >= ` `0` `; i--) {` ` ` ` ` `// Find the bit at i-th position` ` ` `int` `bit = (n >> i) & ` `1` `;` ` ` `if` `(node.nums[bit] == ` `null` `) {` ` ` `node.nums[bit]` ` ` `= ` `new` `TrieNode();` ` ` `}` ` ` `node = node.nums[bit];` ` ` `}` ` ` ` ` `// Update the value` ` ` `node.prefixValue = n;` ` ` `}` ` ` ` ` `// Function to search the root` ` ` `// with the value and perform` ` ` `// the Bitwise XOR with N` ` ` `public` `int` `search(TrieNode root,` ` ` `int` `n)` ` ` `{` ` ` `TrieNode node = root;` ` ` ` ` `// Iterate from 31 to 0` ` ` `for` `(` `int` `i = ` `31` `; i >= ` `0` `; i--) {` ` ` ` ` `// Find the bit at ith` ` ` `// position` ` ` `int` `bit = (n >> i) & ` `1` `;` ` ` `int` `requiredBit = bit` ` ` `== ` `1` ` ` `? ` `0` ` ` `: ` `1` `;` ` ` ` ` `if` `(node.nums[requiredBit]` ` ` `!= ` `null` `) {` ` ` `node = node.nums[requiredBit];` ` ` `}` ` ` `else` `{` ` ` `node = node.nums[bit];` ` ` `}` ` ` `}` ` ` ` ` `// Return the prefixvalue XORed` ` ` `// with N` ` ` `return` `node.prefixValue ^ n;` ` ` `}` `}` ` ` `class` `GFG {` ` ` ` ` `// Driver Code` ` ` `public` `static` `void` `main(String[] args)` ` ` `{` ` ` `sol tt = ` `new` `sol();` ` ` `int` `[] nums = { ` `0` `, ` `1` `, ` `2` `, ` `3` `, ` `4` `};` ` ` `int` `[][] queries = { { ` `3` `, ` `1` `},` ` ` `{ ` `1` `, ` `3` `},` ` ` `{ ` `5` `, ` `6` `} };` ` ` ` ` `tt.maximizeXor(nums, queries);` ` ` `}` `}` |

**Output:**

3 3 7

**Time Complexity:** O(N*log N + K*log K)**Auxiliary Space:** O(N)

Attention reader! Don’t stop learning now. Get hold of all the important DSA concepts with the **DSA Self Paced Course** at a student-friendly price and become industry ready. To complete your preparation from learning a language to DS Algo and many more, please refer **Complete Interview Preparation Course****.**

In case you wish to attend live classes with industry experts, please refer **Geeks Classes Live** and **Geeks Classes Live USA**