Run ID | 作者 | 问题 | 语言 | 测评结果 | 分数 | 时间 | 内存 | 代码长度 | 提交时间 |
---|---|---|---|---|---|---|---|---|---|
30535 | A21μΘ_wjy | 【S】T4 | C++ | 解答错误 | 95 | 424 MS | 34096 KB | 4842 | 2024-07-19 16:45:41 |
#include<bits/stdc++.h> #define int long long using namespace std; //Tree Partition int lc(int p){return p<<1;} int rc(int p){return p<<1|1;} const int mod=1e9+7; int n; const int maxn=1e5+7; int val[maxn]; int a[maxn]; vector<int> E[maxn]; int dfn[maxn]; int idx[maxn]; int fa[maxn]; int hs[maxn]; int dep[maxn]; int sz[maxn]; int top[maxn]; int cnt=0; inline void dfs1(int u,int f,int d){ dep[u]=d; fa[u]=f; sz[u]=1; int mx=0; for(int i=0;i<E[u].size();i++){ int v=E[u][i]; if(v==f)continue; dfs1(v,u,d+1); sz[u]+=sz[v]; if(sz[v]>mx){ mx=sz[v]; hs[u]=v; } } } inline void dfs2(int u,int topf){ idx[++cnt]=u; dfn[u]=cnt; top[u]=topf; if(!hs[u])return; dfs2(hs[u],topf); for(int i=0;i<E[u].size();i++){ int v=E[u][i]; if(v!=fa[u]&&v!=hs[u])dfs2(v,v); } } struct SGT{ struct node{ int tag; int sum; }d[maxn<<2]; inline void pushup(int p){ d[p].sum=(d[lc(p)].sum+d[rc(p)].sum)%mod; } inline void pushdown(int p,int l,int r){ int mid=l+r>>1; int tg=d[p].tag; d[lc(p)].sum=(d[lc(p)].sum+(mid-l+1)*tg)%mod; d[rc(p)].sum=(d[rc(p)].sum+(r-mid)*tg)%mod; d[lc(p)].tag=(d[lc(p)].tag+tg)%mod; d[rc(p)].tag=(d[rc(p)].tag+tg)%mod; d[p].tag=0; } inline void build(int p,int l,int r){ if(l==r){ d[p].sum=a[l]; d[p].tag=0; return; } int mid=l+r>>1; d[p].tag=0; build(lc(p),l,mid); build(rc(p),mid+1,r); pushup(p); } inline void update(int p,int l,int r,int al,int ar,int dt){ if(al<=l&&r<=ar){ d[p].tag=(d[p].tag+dt)%mod; d[p].sum=(d[p].sum+(r-l+1)*dt)%mod; return; } pushdown(p,l,r); int mid=l+r>>1; if(al<=mid)update(lc(p),l,mid,al,ar,dt); if(ar>mid)update(rc(p),mid+1,r,al,ar,dt); pushup(p); } inline int query(int p,int l,int r,int al,int ar){ if(al<=l&&r<=ar){ return d[p].sum; } pushdown(p,l,r); int sum=0; int mid=l+r>>1; if(al<=mid)sum=(sum+query(lc(p),l,mid,al,ar))%mod; if(ar>mid)sum=(sum+query(rc(p),mid+1,r,al,ar))%mod; return sum; } }T; inline void addtree(int u,int dt){ T.update(1,1,n,dfn[u],dfn[u]+sz[u]-1,dt); } inline int qrytree(int u){ return T.query(1,1,n,dfn[u],dfn[u]+sz[u]-1); } inline void addpath(int u,int v,int dt){ while(top[u]!=top[v]){ if(dep[top[u]]>dep[top[v]]){ T.update(1,1,n,dfn[top[u]],dfn[u],dt); u=fa[top[u]]; } else{ T.update(1,1,n,dfn[top[v]],dfn[v],dt); v=fa[top[v]]; } } if(dep[u]<dep[v])T.update(1,1,n,dfn[u],dfn[v],dt); else T.update(1,1,n,dfn[v],dfn[u],dt); } inline int qrypath(int u,int v){ int ans=0; while(top[u]!=top[v]){ if(dep[top[u]]>dep[top[v]]){ ans=(ans+T.query(1,1,n,dfn[top[u]],dfn[u]))%mod; u=fa[top[u]]; } else{ ans=(ans+T.query(1,1,n,dfn[top[v]],dfn[v]))%mod; v=fa[top[v]]; } } if(dep[u]<dep[v])ans=(ans+T.query(1,1,n,dfn[u],dfn[v]))%mod; else ans=(ans+T.query(1,1,n,dfn[v],dfn[u]))%mod; return ans; } inline int qpow(int a,int b){ int ans=1; while(b){ if(b&1)ans=ans*a%mod; a=a*a%mod; b>>=1; } return ans; } int l[maxn],r[maxn]; int G[maxn],P=1; int iG[maxn]; int C; vector<int> Lp[maxn]; vector<int> Rp[maxn]; int F1,F2,F3; signed main(){ cin>>n; for(int i=1;i<=n;i++){ cin>>l[i]>>r[i]; G[i]=r[i]-l[i]+1; P=P*G[i]%mod; C=max(C,r[i]); iG[i]=qpow(G[i],mod-2); Lp[l[i]].push_back(i),Rp[r[i]].push_back(i); } for(int i=1;i<n;i++){ int u,v; cin>>u>>v; E[u].push_back(v); E[v].push_back(u); } dfs1(1,1,1); dfs2(1,1); T.build(1,1,n); int Cl=0; int ans=0; for(int c=1;c<=C;c++){ for(int j=0;j<Lp[c].size();j++){ int i=Lp[c][j]; F1=(F1+dep[i]*iG[i]%mod)%mod; F2=(F2+iG[i])%mod; F3=(F3+dep[i]*iG[i]%mod*iG[i]%mod)%mod; Cl=(Cl+qrypath(1,i)*iG[i]%mod)%mod; addpath(1,i,iG[i]); } ans=(ans+F1*F2%mod-F3+mod-2*Cl%mod+mod)%mod; for(int j=0;j<Rp[c].size();j++){ int i=Rp[c][j]; F1=(F1-dep[i]*iG[i]+mod)%mod; F2=(F2-iG[i]+mod)%mod; F3=(F3-dep[i]*iG[i]%mod*iG[i]%mod+mod)%mod; addpath(1,i,mod-iG[i]); Cl=(Cl-qrypath(1,i)*iG[i]%mod+mod)%mod; } } cout<<ans*P%mod<<endl; }