以一道区间和查询来说明板子如何使用
1.merge的时候只需要维护两个根节点的距离,利用的是合并时题目给的信息
2.find的时候更新维护是子节点到根的距离
3.需要加一个查询函数,因为距离数组是开在结构体内部的。
题目描述
对于一个长度为 \(N\) 的整数数列 \(A_{1}, A_{2}, \cdots A_{N}\),小蓝想知道下标 \(l\) 到 \(r\) 的部分和 \(\sum\limits_{i=l}^{r}A_i=A_{l}+A_{l+1}+\cdots+A_{r}\) 是多少?
然而,小蓝并不知道数列中每个数的值是多少,他只知道它的 \(M\) 个部分和的值。其中第 \(i\) 个部分和是下标 \(l_{i}\) 到 \(r_{i}\) 的部分和 \(\sum_{j=l_{i}}^{r_{i}}=A_{l_{i}}+A_{l_{i}+1}+\cdots+A_{r_{i}}\), 值是 \(S_{i}\) 。
对于所有评测用例, \(1 \leq N, M, Q \leq 10^{5},-10^{12} \leq S_{i} \leq 10^{12}, 1 \leq l_{i} \leq r_{i} \leq N\), \(1 \leq l \leq r \leq N\) 。数据保证没有矛盾。
蓝桥杯 2022 省赛 A 组 J 题。
#include <bits/stdc++.h>
using namespace std;
#define ll long long
# define int long long
#define ull unsigned long long
#define pii pair<int,int>
#define baoliu(x, y) cout << fixed << setprecision(y) << x
#define endl "\n"
#define debug1(x) cerr<<x<<" "
#define debug2(x) cerr<<x<<endl
const int N = 2e5 + 10;
const int M = 1e6 + 10;
const int inf = 0x3f3f3f3f;
const int mod = 998244353;
const double eps = 1e-8;
int n, m;
int a[N];
struct DSU {
vector<int> f, siz,d;
DSU() {}
DSU(int n) {
init(n);
}
void init(int n) {
f.resize(n);
std::iota(f.begin(), f.end(), 0);
siz.assign(n, 1);
d.resize(n);
for(int i=0;i<n;i++)d[i]=0;
}
int find(int x)
{
if (f[x] != x)
{
int root = find(f[x]);
d[x] += d[f[x]];//f[x]到根距离已经被更新
f[x] = root;//让x指向根
}
return f[x];
}
bool same(int x, int y) {
return find(x) == find(y);
}
bool merge(int l, int r,int add) {
int x = find(l);
int y = find(r);
if (x == y) {
return false;
}
d[y]=d[l]+add-d[r];
siz[x] += siz[y];
f[y] = x;
return true;
}
int size(int x) {
return siz[find(x)];
}
int query(int u,int v){
int ans=d[v]-d[u];
return ans;
}
};
void solve(){
int q;
cin>>n>>m>>q;
DSU dsu(n+5);
for(int i=1;i<=m;i++){
int sum=0;
int u,v;cin>>u>>v>>sum;
u--;
dsu.merge(u,v,sum);//根节点是最小值
}
for(int i=1;i<=q;i++){
int u,v;cin>>u>>v;
u--;
if(dsu.same(u,v)){
int ans=dsu.query(u,v);
cout<<ans<<endl;
}
else {
cout<<"UNKNOWN"<<endl;
}
}
}
signed main() {
cin.tie(0);
ios::sync_with_stdio(false);
int t;
//cin>>t;
t=1;
while (t--) {
solve();
}
return 0;
}
标签:dsu,int,sum,查集,long,板子,leq,带权,define
From: https://www.cnblogs.com/mathiter/p/18048859