Primes and Queries - Google Kickstart 2021 Round D第四题
You are given a prime number P.
Let’s define V(x) as the degree of P in the prime factorization of x. To be clearer, if V(x)=y then x is divisible by P y P^y Py, but not divisible by P y + 1 P^{y+1} Py+1.
Also we define V(0)=0.
For example, when P=3, and x=45, since 45=5⋅32, therefore V(45)=2.
You are also given an array A with N elements. You need to process Q queries of 2 types on this array:
type 1 query: 1 pos val - assign a value val to the element at pos, i.e. A p o s = v a l A_{pos}=val Apos=val
type 2 query: 2 S L R - print ∑ i = L R V ( A i S − ( A i ( m o d P ) ) S ) \sum_{i=L}^RV(A_i^S−(A_i\pmod P)^S) ∑i=LRV(AiS−(Ai(modP))S).
题目大意
给定一个素数
P
P
P,定义
V
(
x
)
V(x)
V(x)为
P
P
P在
x
x
x质因子分解里的度数(比如质数是2,20可以被4整除,不能被8整除,20的度数就是2),定义
V
(
0
)
=
0
V(0)=0
V(0)=0。 现在给定一个长度为
N
N
N的序列(
1
≤
N
≤
5
∗
1
0
5
1\leq N\leq5*10^5
1≤N≤5∗105),试处理
Q
Q
Q个操作(
1
≤
Q
≤
1
0
5
1\leq Q\leq10^5
1≤Q≤105)。操作有如下两种:
1.
1
p
o
s
v
a
l
1 \space pos\space val
1 pos val:把第
p
o
s
pos
pos个数改为
v
a
l
val
val ;
2.
2
S
L
R
2\space S\space L\space R
2 S L R:输出
∑
i
=
L
R
V
(
A
i
S
−
(
A
i
(
m
o
d
P
)
)
S
)
\sum_{i=L}^RV(A_i^S−(A_i\pmod P)^S)
∑i=LRV(AiS−(Ai(modP))S).
思路分析
很明显是一道线段树问题,修改就不说了,区间求和只是看上去复杂一点。为了方便我们令
B
=
A
(
m
o
d
P
)
B=A\pmod P
B=A(modP),那么
A
i
S
−
(
A
i
(
m
o
d
P
)
)
S
=
A
i
S
−
B
i
S
A_i^S−(A_i\pmod P)^S=A_i^S-B_i^S
AiS−(Ai(modP))S=AiS−BiS
注意到
A
i
A_i
Ai和
B
i
B_i
Bi模
P
P
P同余,我们分情况讨论:
1.
P
∣
A
i
P\space|A_i
P ∣Ai:每一项的贡献
V
(
A
i
S
−
B
i
S
)
=
V
(
A
i
−
B
i
)
+
V
(
S
∗
A
i
S
)
=
V
(
A
i
−
B
i
)
+
S
∗
V
(
A
i
S
)
V(A_i^S-B_i^S)=V(A_i-B_i)+V(S*A_i^S)=V(A_i-B_i)+S*V(A_i^S)
V(AiS−BiS)=V(Ai−Bi)+V(S∗AiS)=V(Ai−Bi)+S∗V(AiS)。
2.
P
∤
A
i
P\not|A_i
P∣Ai: 我们用提升指数引理:如果P是2且
S
S
S为偶数,那么
V
(
A
i
S
−
B
i
S
)
=
V
(
A
i
−
B
i
)
+
V
(
A
i
+
B
i
)
+
V
(
S
)
−
1
V(A_i^S-B_i^S)=V(A_i-B_i)+V(A_i+B_i)+V(S)-1
V(AiS−BiS)=V(Ai−Bi)+V(Ai+Bi)+V(S)−1,否则
V
(
A
i
S
−
B
i
S
)
=
V
(
A
i
−
B
i
)
+
V
(
S
∗
A
i
S
)
=
V
(
A
i
−
B
i
)
+
V
(
S
)
V(A_i^S-B_i^S)=V(A_i-B_i)+V(S*A_i^S)=V(A_i-B_i)+V(S)
V(AiS−BiS)=V(Ai−Bi)+V(S∗AiS)=V(Ai−Bi)+V(S)。
V V V这个函数的复杂度上界只有 l o g ( n ) log(n) log(n),所以我们每次可以直接暴力计算。我们建立两颗线段树,一颗上面是所有当前能被整除的项,一颗是所有不能被整除的项。修改时,如果被修改的数从不能被整除变成可以被整除,只需要把第二颗树上的当前位置归零,再在第一棵树上修改即可,反之亦然。求和时,把两棵树的结果加起来就可以了。注意一下如果质数是2的话,那么我们第二颗树上记录的应当是 V ( A i − B i ) + V ( A i + B i ) V(A_i-B_i)+V(A_i+B_i) V(Ai−Bi)+V(Ai+Bi),小细节不要忘记。
分析一下时间复杂度:就是一般线段树的时间复杂度,外加建树时需要额外预处理 V V V函数的值,总复杂度是 O ( N l o g ( A i ) + Q ( l o g N + l o g S ) ) O(Nlog(A_i)+Q(logN+logS)) O(Nlog(Ai)+Q(logN+logS))。
题目比较水,可以算是纯数学题了,没什么技巧可言,希望以后的题目能更有新意。