zoukankan      html  css  js  c++  java
  • CodeForces 1487C Minimum Ties(建图、模拟)

    Problem - C - Codeforces

    题目大意:

    给定一个完全图,每个队伍就是一个点,每场比赛就是一条无向边。现在每次可以消掉一个环,使得剩下的边最少。

    思路:

    有这样一个结论,将一个完全图分成若干个环逐个消去,所有节点出现在所有环上的总次数都相同。

    举个例子,比如六阶完全图,可以拆成(0-index):

    0 1 2 3 4 5 
    0 2 4 
    1 3 5
    

    三个环,每个节点都总共出现了两次。

    接下来我们可以 \(\mathcal O(n^3)\) 的进行模拟删环,记录答案。

    枚举起点和步长,再 check 是否能构成环,如能构成则标记。

    Code:
    int main() {
        ios::sync_with_stdio(false); cin.tie(0); cout.tie(0);
        int T; cin >> T;
        while (T--) {
            int n; cin >> n;
            vector<vector<int>> ans(n, vector<int>(n)); //胜负关系,即答案
            vector<vector<int>> ck(n, vector<int>(n)); //边被占用为1
            for (int st = 0; st < n; st++) {
                for (int len = 1; len < n; len++) {
                    vector<bool> vis(n); //点的访问情况
                    int now = st;
                    bool ok = true;
                    while (!vis[now]) {
                        vis[now] = true;
                        int nxt = (now + len) % n;
                        if (!ans[now][nxt] && !ans[nxt][now] && !ck[now][nxt] && !ck[nxt][now]) {
                            ck[now][nxt] = ck[nxt][now] = 1;
                            now = nxt;
                        } else {
                            ok = false;
                            break;
                        }
                    }
                    fill(vis.begin(), vis.end(), false);
                    now = st;
                    while (!vis[now]) { //线性删除边占用标记,不然会超时
                        vis[now] = true;
                        int nxt = (now + len) % n;
                        ck[now][nxt] = ck[nxt][now] = 0;
                    }
                    if (!ok) {
                        continue;
                    }
                    now = st;
                    fill(vis.begin(), vis.end(), false);
                    while (!vis[now]) {
                        // cerr << now << " ";
                        vis[now] = true;
                        int nxt = (now + len) % n;
                        ans[now][nxt] = 1;
                        ans[nxt][now] = -1;
                        now = nxt;
                    }
                    // cout << endl;
                }
            }    
            // cout << "####" << endl;    
            for (int i = 0; i < n; i++) {
                for (int j = i + 1; j < n; j++) {
                    cout << ans[i][j] << " \n"[j == n - 1 && i == n - 2];
                }
            }
        }
        return 0;
    }
    
  • 相关阅读:
    接口测试--apipost中cookie管理器的使用
    python解释器换了路径,导致pip安装失败解决方法
    Jmeter之Bean shell使用(二)
    Jmeter之Bean shell使用(一)
    BeanShell生成随机数
    Jmeter之Json 提取器
    Jmeter全面信息学习笔记
    python模块之codecs
    open()和with open()的区别
    【图像处理】第二次实验:二维快速傅里叶变换与离散余弦变换
  • 原文地址:https://www.cnblogs.com/Nepenthe8/p/15625911.html
Copyright © 2011-2022 走看看