在給定的n個整數a1,a2……an中選出兩個進行xor(異或)運算,得到的結果最大是多少?
輸入格式
第一行輸入乙個整數n。
第二行輸入n個整數a1~an。
輸出格式
輸出乙個整數表示答案。
資料範圍
1≤n≤105,
0≤ai<231
輸入樣例:
31 2 3
輸出樣例:
3(基於貪心的思想)
異或是一種不進製加法(基於二進位制的方法下)。0 xor 1=1,本身異或本身結果為0;
那麼就可以想到一種貪心的方法是:乙個數和乙個與自己的每乙個二進位制位都不相同的數字異或,這樣子的結果一定最優。
如果說是純暴力的寫for迴圈,這樣子的話,應該是o(n^2)的做法:
第一層列舉每乙個數字;
第二層在列舉每乙個數字,與之異或。
所以說:應該要優化成o(n)或者是o(nlogn)的。
此時就可以想到字典樹(trie樹):
把每乙個數字的二進位制位保留到樹上;
這樣子的話,再每遍歷一遍整個數字,就是o(nlogn)的複雜度。
為什麼說是基於貪心的呢??
首先是按位異或,給每一位都找到乙個可以異或出來最大的數字;
其次是按最高位異或,這樣子的話,找到乙個可以異或的數字就是使得異或的最大值增加最多的。
#include#includeusing namespace std;
const int n=100000+10,m=31*100000+10;//m節點個數
int a[n];
int n;
//定義tire
int son[m][2],idx;
void insert(int x)
p=son[p][s];
}}int search(int x)
int res=0;
for(int i=0;ires=max(res,search(a[i]));
cout
}
字典樹 最大異或對
分析程式 最大異或對,就是給出一堆數,然後在這一堆數中選擇兩個數,使得異或後結果最大。所涉及到的知識點有 字典樹,二進位制的思想 這樣寫不出意外是會超時的,因為這樣看的話,他的時間複雜度是o n n 然後題中給出的資料是10的五次方。所以說這樣的話,需要執行10的十次方次操作,而機器在一秒中只能執行...
最大異或對 字典樹)
143.最大異或對 在給定的n個整數a1,a2 an a1,a2 an 中選出兩個進行xor 異或 運算,得到的結果最大是多少?輸入格式 第一行輸入乙個整數n。第二行輸入n個整數a 1 a1 an an 輸出格式 輸出乙個整數表示答案。資料範圍1 n 105 1 n 10 5,0 ai 231 0 ...
字典樹 最大異或對
給你 n 個數,從中選兩個數進行異或運算,得到結果最大是多少 一道沒寫過就不知道怎麼寫的套路題 剛開始可以用貪心分析,也就是說如果兩個數的高位能夠盡可能的大那麼我們就盡可能的大就好了,也就是說兩個數的二進位制數在同一位不同,此時最大,那麼怎樣很快的滿足呢?我們發現可以將二進位制數轉化到trie上面解...