题目大意:
EZ同学家里非常富有,但又极其的谦虚,说话又好听,是个不可多得的人才。
EZ常常在假期环游世界,他准备去N(N<=100000)个国家之多,一些国家有航线连接,由于EZ同学有一定的强迫症,任意两个国家之间都能通过航路直接或间接到达,并且这样的路径仅有一种。(简单来说,这些国家构成了一棵树)
由于EZ是C国人,因此将C国(1号国家)作为整棵树的根
每个国家有一个旅游热度A[i]和影响力D[i]。由于目的地有点多,为了避免选择困难症,他给每个国家设置了一个向往值F[i],它等于所有的A[j]之和,满足i国在j国向C国走D[j]步的路径上(经过一条航路算一步,i=j也会被统计,如果D[j]步超过了C国,则超出部分不用管)。
LYD同学家里有矿,富有程度与EZ不相上下,但他却在宅与现充间摇摆不定。某次机缘巧合,EZ外出旅游刺激了LYD,他决定也要开始旅游。为了避免又被判高重复率导致被取消资格,他将EZ的旅游地图略微做了一点调整,每条航路将有一定的概率出现。
现在他有Q个询问,每次询问某个国家所在的联通块(由于每条边是一定概率出现,因此它所在的联通块可以是很多种)中所有国家的F[i]值的和的平方的期望(对998244353取模),以此来决定他旅游的目的地。但他极其厌恶繁琐的计算,于是他找到了能算出圆周率并将它倒背下来的你,答应给你丰厚的报酬。家里没矿,老爸也不是X达集团老总的你决定接受他的任务。
思路:
先考虑f怎么求,我们可以在每个点X打上+的标记,在d[i]+1祖宗打上-的标记。然后dfs一次就可以求出来f了,不需要树剖。
然后考虑则维护合的平方的希望。因为 ( a + b ) 2 = a 2 + 2 ∗ a ∗ b + b 2 (a+b)^2=a^2+2*a*b+b^2 (a+b)2=a2+2∗a∗b+b2,所以我们要记录每个子树的和和每个子树平方和。然后合并的时候就很简单了,这样一次dfs就可以求出f[1]的答案了。
然后怎么求其他点的答案呢,我们对于一个一个点只要知道他父亲过来平方和,和和,然后用前缀和优化一下每个兄弟的转移就好了。
程序:
#include<cstring>
#include<iostream>
#include<algorithm>
#include<cstdio>
#define LL long long
using namespace std;
const LL N=200005;
const LL mo=998244353;
LL fa[N][21],vd[N],fg[N],fh[N],f[N],g[N],ans[N],last[N],a[N],d[N],t[N],love[N];
LL n,sb,cnt;
struct tree{
LL to,next