ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

「codeforces - 687D」Dividing Kingdom II

2022-08-08 16:34:22  阅读:566  来源: 互联网

标签:Kingdom md return int res dst 687D II fa


link。

好题啊。

首先有一个类 kruskal 暴力,就是对于每一个询问,把所有边按权值大小排降序,第一个加进去成为奇环的边就是答案。注意我们不需要关注偶环长成什么样子,所以我们实际上维护的是一棵生成树。这个可以用并查集维护结点到根的边的数量来实现。

因此我们需要关注的边只有 \(O(n)\) 条了(生成树),那么维护一个区间的需要关注的边的边集,具体而言就是树边和奇环上的边。考虑用线段树,合并的时候用归并即可。

int n, m, q, fa[2100], dst[2100], ms, mh;
int u[1000100], v[1000100], w[1000100];
vi<bsi<int>> md;
bool flag;
int ldr(int x) {
    if (x != fa[x]) {
        int u = ldr(fa[x]);
        dst[x] ^= dst[fa[x]];
        return fa[x] = u;
    }
    return x;
}
int mrg(int x, int y) {
    int u = ldr(x), v = ldr(y);
    if (u == v) {
        if (dst[x] == dst[y]) return 2;
        return 0;
    }
    fa[v] = u;
    dst[v] = dst[x]^dst[y]^1;
    return 1;
}
bsi<int> mrg(const bsi<int>& lhs, const bsi<int>& rhs) {
    bsi<int> qwq, res;
    merge(lhs.begin(), lhs.end(), rhs.begin(), rhs.end(), back_inserter(qwq), [&](int x, int y) {
        return w[x] > w[y];
    });
    for (auto i : qwq) {
        fa[u[i]] = u[i], fa[v[i]] = v[i];
        dst[u[i]] = dst[v[i]] = 0;
    }
    for (auto i : qwq) {
        int tmp = mrg(u[i], v[i]);
        if (tmp) res += i;
        if (tmp == 2) {
            flag = 1;
            break;
        }
    }
    return res;
}
void upd(int now) {
    md[now] = mrg(md[now*2], md[now*2+1]);
}
int qry(int l, int r) {
    bsi<int> res;
    flag = 0;
    for (l += ms-1, r += ms; l < r; l >>= 1, r >>= 1) {
        if (l&1) res = mrg(res, md[l++]);
        if (r&1) res = mrg(md[--r], res);
    }
    if (flag) return w[res.back()];
    return -1;
}
signed main() {
    ios::sync_with_stdio(0);
    cin.tie(0);
    cin >> n >> m >> q;
    mh = ceil(log2(m)), ms = 1<<mh;
    md = vi<bsi<int>>(ms*2, bsi<int>());
    for (int i=1; i<=m; ++i) {
        cin >> u[i] >> v[i] >> w[i];
    }
    for (int i=1; i<=m; ++i) {
        md[i+ms-1] = bsi<int>({i});
    }
    for (int i=ms-1; i>=1; --i) {
        upd(i);
    }
    for (int l,r; q--;) {
        cin >> l >> r;
        cout << qry(l, r) << "\n";
    }
}

标签:Kingdom,md,return,int,res,dst,687D,II,fa
来源: https://www.cnblogs.com/orchid-any/p/16562330.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有