当前位置:   article > 正文

异或和 蓝桥杯2024python省赛 题解_蓝桥杯2024 python

蓝桥杯2024 python

异或和

题意

在这里插入图片描述
经典的树上单点修改+子树求和的问题。那么我们首先可以想到构建出树的dfs序,将原本一棵树上的内容转化为一个数组。再由于异或运算和加法一样具有可逆性,所以使用树状数组维护即可。

然后由于树状数组维护的性质有限,每次只能额外异或一个数而不能直接进行赋值,所以我们保留好原数组,每次给单点赋值时,视为异或上“原来的值异或现在的值”就可以了。复杂度为 O(mlogn)。

附上python代码

import sys
from collections import Counter
from heapq import *
input = lambda: sys.stdin.readline().strip()
n, m = map(int, input().split())
a = [0] * (100000 + 10)
temp = list(map(int, input().split()))
a[1 : n + 1] = temp
e = [[] for _ in range(100000 + 5)]
for i in range(n - 1):
    x, y = map(int, input().split())
    e[x].append(y)
    e[y].append(x)
tr = [0] * (200000 + 101)
l = [0] * (200000 + 10)
r = [0] * (200000 + 10)
N = 200000 + 100
timestamp = 0

def dfs(u: int, fa: int):
    global timestamp
    timestamp += 1
    l[u] = timestamp
    for v in e[u]:
        if v != fa:
            dfs(v, u)
    timestamp += 1
    r[u] = timestamp


dfs(1, -1)


def lowbit(x):
    return x & -x


def add(x, k):
    i = x
    while i <= N:
        tr[i] ^= k
        i += lowbit(i)


def query(x):
    res, i = 0, x
    while i > 0:
        res ^= tr[i]
        i -= lowbit(i)
    return res


for i in range(1, n + 1):
    add(l[i], a[i])
for _ in range(m):
    p = list(map(int, input().split()))
    if p[0] == 1:
        x, y = p[1], p[2]
        add(l[x], a[x] ^ y)
        a[x] = y
    else:
        x = p[1]
        print(query(r[x]) ^ query(l[x] - 1))
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/羊村懒王/article/detail/466597
推荐阅读
相关标签
  

闽ICP备14008679号