日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

2021中超1 1006 xor sum

發布時間:2025/3/12 编程问答 23 豆豆
生活随笔 收集整理的這篇文章主要介紹了 2021中超1 1006 xor sum 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

2021杭電1 1006 xor sum

給定n個數和一個數k,求出最短的連續的一段數,使得它們的異或和大于等于k,如果沒有則輸出-1。
其中1<=n<=1e5,0<=k, ai<=2^30

之前還沒有做過這個類型的題,隊友給我說可以用trie來搞,存個前綴和,然后就不會了。沿著這個想法亂搞了一下,發現還可以做,寫了出來發現還真能過樣例,調了一下(init忘了調用)就過了。

大致思路是這樣的:trie上有0,1兩個分支,從左到右枚舉n個數,求出前綴異或和,轉二進制塞到trie里面,同時trie上的節點存的是編號,也就是當前是1到編號i的前綴異或和。

每一次的詢問,將k和xor_sum[i]帶進去,然后從高位到低位求出trie上存的前綴和與xor_sum[i]的異或和,當這個值已經大于k的時候,就可以直接返回當前節點所存的編號;如果這個值加上后面都是1還是小于k的時候,說明達不到k,可以直接返回0。

因為r是確定的,我們需要求出的是l最大,因此insert的時候編號應該是大的覆蓋小的,又insert的編號是從1到n,所以每次直接覆蓋就行了。在query求解的時候就找出可行的前綴和編號的最大值就可以了。

由于我是mx初值設為0,所以要特判一下,特判就是當前的xor_sum已經是大于k的時候,那么l = 1, r = i一定是符合條件的一組解。

const int N = 1e5 + 10; int trie[N * 31][2], mx[N * 31], fa[N * 31], tot = 0;void init() {trie[0][0] = trie[0][1] = 0;for (int i = 0; i <= tot; i ++){mx[i] = fa[i] = 0;}tot = 0; }void insert(int x, int pos) {int temp[31];for (int i = 30; i >= 1; i --){temp[i] = x & 1;x >>= 1;}int now = 0;for (int i = 1; i <= 30; i ++){int p = now;mx[now] = pos;if (trie[now][temp[i]])now = trie[now][temp[i]];else{trie[now][temp[i]] = ++ tot;trie[tot][0] = trie[tot][1] = 0;now = tot;}fa[now] = p;}mx[now] = pos; }int query(int r, int k, int now, int sum, int bit) {if (sum >= k)return mx[now];if (sum + (1 << (bit + 1)) <= k)return 0;int ans = 0;if (trie[now][0]){int temp = (r & (1 << bit));ans = max (ans, query(r, k, trie[now][0], sum + temp, bit - 1));}if (trie[now][1]){int temp = (r & (1 << bit) ^ (1 << bit));ans = max(ans, query(r, k, trie[now][1], sum + temp, bit - 1));}return ans; }int main() {//freopen("data.txt", "r", stdin);//freopen("out.txt", "w", stdout);int T = 1;T = read();while (T --){init();int n, k;n = read(); k = read();int ans = n + 1, l = -1, r = -1;int sum = 0;for (int i = 1; i <= n; i ++){int a = read();sum ^= a;if (sum >= k){if (ans > i){ans = i;l = 1;r = i;}}int d = query(sum, k, 0, 0, 29);if (d > 0 && ans > i - d){ans = i - d;l = d + 1;r = i;}insert(sum, i);}if (ans == n + 1)printf ("-1\n");elseprintf ("%d %d\n", l, r);} } 與50位技術專家面對面20年技術見證,附贈技術全景圖

總結

以上是生活随笔為你收集整理的2021中超1 1006 xor sum的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。