题目
给定一串手链,每个珠子被赋予一个价值w[i],现要从中截取连续的一段,使得他们的异或和最大(注意,手链还未串上)
格式:
输入格式:第一行包含一个正整数N
第二行N个正整数wi,表示珠子价格
输出格式:一个正整数,输出最大异或和
思路:
题目相当于求子数组(正整数)的最大异或和
代码:
import java.util.Scanner;
public class Main {
private static int solve(int[] data) {
if (data == null || data.length == 0) {
return 0;
}
Trie trie = new Trie();
trie.add(0);
int sum = 0;
int ret = data[0];
for (int i = 0; i < data.length; ++i) {
sum ^= data[i];
ret = Math.max(ret, trie.query(sum));
trie.add(sum);
}
return ret;
}
public static void main(String[] args) {
Scanner in = new Scanner(System.in);
while (in.hasNext()) {
int n = in.nextInt();
int[] arr = new int[n];
for (int i = 0; i < n; ++i) {
arr[i] = in.nextInt();
}
System.out.println(solve(arr));
}
}
}
class Trie {
private Node root;
class Node {
Node[] children = new Node[2];
}
public Trie() {
this.root = new Node();
}
public void add(int n) {
Node cur = this.root;
for (int i = 31; i >= 0; --i) {
int digit = (n >> i) & 1;
if (cur.children[digit] == null) {
cur.children[digit] = new Node();
}
cur = cur.children[digit];
}
}
public int query(int n) {
Node cur = this.root;
int ret = 0;
for (int i = 31; i >= 0; --i) {
int digit = (n >> i) & 1;
int best = i == 31 ? digit : digit ^ 1;
if (cur.children[best] == null) {
best ^= 1;
}
ret |= ((best ^ digit) << i);
cur = cur.children[best];
}
return ret;
}
}