• topcoder srm 685 div1


    problem1 link

    依次枚举每个元素$x$,作为$S$中开始选择的第一个元素。对于当前$S$中任意两个元素$i,j$,若$T[i][j]$不在$S$中,则将其加入$S$,然后继续扩展;若所有的$T[i][j]$都在$S$中,则结束扩展。每次扩展结束之后保存$|S|$的最小值。

    problem2 link

    总的思路是搜索,分别枚举每一条边是在哪个集合中,进行如下的优化:

    (1)使用并查集,当其中两个集合都联通时结束;当有一个集合联通时,直接判断剩下所有的边加入另一个集合能否使得另一个集合联通;

    (2)如果当前剩下所有的边都加入到其中一个集合都不能使其联通时,结束搜索返回;

    (3)当前边加入第一个集合使其联通分量减少时才进行加入的操作,否则不再继续搜索下去,而将其直接加入另一个集合。

    problem3 link

    随即生成1000个点数为12个图,然后计算最小生成树的个数。假设可以从中选出四个(可能是相同的)然后串联起来,那么答案就是$A_{1}*A_{2}*A_{3}*A_{4}$。$A_{i}$为选出的第$i$个图的最小生成树的个数。

    code for problem1

    #include <algorithm>
    #include <vector>
    
    class MultiplicationTable2 {
     public:
      int minimalGoodSet(const std::vector<int> &a) {
        int n2 = static_cast<int>(a.size());
        int n = 1;
        while (n * n != n2) {
          ++n;
        }
        std::vector<std::vector<int>> g(n, std::vector<int>(n));
        auto Compute = [&](int x) {
          if (g[x][x] == x) {
            return 1;
          }
          std::vector<int> s;
          std::vector<bool> h(n);
          s.push_back(x);
          h[x] = true;
          while (true) {
            bool ok = true;
            std::vector<int> ns = s;
            for (size_t i = 0; i < s.size(); ++i) {
              for (size_t j = 0; j < s.size(); ++j) {
                int k = g[s[i]][s[j]];
                if (!h[k]) {
                  h[k] = true;
                  ns.push_back(k);
                  ok = false;
                }
              }
            }
            if (ok) {
              break;
            }
            s = ns;
          }
          return static_cast<int>(s.size());
        };
        for (int i = 0; i < n; ++i) {
          for (int j = 0; j < n; ++j) {
            g[i][j] = a[i * n + j];
          }
        }
        int result = n;
        for (int i = 0; i < n; ++i) {
          result = std::min(result, Compute(i));
        }
        return result;
      }
    };

    code for problem2

    #include <string>
    #include <vector>
    
    constexpr int kMaxN = 10;
    
    struct UnionSet {
      int a[kMaxN];
      int cnt;
      int n;
    
      void Init(int n) {
        this->n = n;
        for (int i = 0; i < n; ++i) {
          a[i] = i;
        }
        cnt = 0;
      }
    
      int Get(int x) {
        if (a[x] != x) {
          a[x] = Get(a[x]);
        }
        return a[x];
      }
    
      bool Update(int x, int y) {
        x = Get(x);
        y = Get(y);
        if (x == y) {
          return false;
        }
        if (x < y) {
          a[y] = x;
        } else {
          a[x] = y;
        }
        ++cnt;
        return true;
      }
      bool OK() { return cnt == n - 1; }
    };
    
    int n, m;
    std::vector<int> a, b;
    
    bool Check(UnionSet s, int id) {
      if (s.OK()) {
        return 1;
      }
      if (id >= m) {
        return 0;
      }
      for (int i = id; i < m && !s.OK(); ++i) {
        s.Update(a[i], b[i]);
      }
      return s.OK();
    }
    
    bool Dfs(int id, UnionSet s1, UnionSet s2) {
      if (s1.OK() && s2.OK()) {
        return 1;
      }
      if (s1.OK()) {
        return Check(s2, id);
      }
      if (s2.OK()) {
        return Check(s1, id);
      }
    
      if (!Check(s1, id) || !Check(s2, id)) {
        return false;
      }
    
      if (id >= m) {
        return false;
      }
    
      while (id < m) {
        if (s1.Get(a[id]) != s1.Get(b[id])) {
          UnionSet new_s1 = s1;
          new_s1.Update(a[id], b[id]);
          if (Dfs(id + 1, new_s1, s2)) {
            return 1;
          }
        }
        s2.Update(a[id], b[id]);
        ++id;
      }
      return false;
    }
    
    class FoxAirline2 {
     public:
      std::string isPossible(int node_number, const std::vector<int> &ea,
                             const std::vector<int> &eb) {
        n = node_number;
        a = ea;
        b = eb;
        m = static_cast<int>(a.size());
    
        UnionSet s1, s2;
        s1.Init(n);
        s2.Init(n);
        if (Dfs(0, s1, s2)) {
          return "Possible";
        }
        return "Impossible";
      }
    };

    code for problem3

    #include <cstdlib>
    #include <ctime>
    #include <unordered_map>
    #include <vector>
    
    class MSTCounter {
     public:
      static int Pow(long long a, int b, int mod) {
        long long result = 1;
        while (b > 0) {
          if (b % 2 == 1) {
            result = result * a % mod;
          }
          a = a * a % mod;
          b /= 2;
        }
        return static_cast<int>(result);
      }
      static int Solver(const std::vector<std::vector<bool>> &g, int mod) {
        int n = static_cast<int>(g.size());
        std::vector<std::vector<int>> a(n, std::vector<int>(n));
        for (int i = 0; i < n; ++i) {
          for (int j = 0; j < n; ++j) {
            if (i != j && g[i][j]) {
              a[i][j] = mod - 1;
              a[i][i] += 1;
            }
          }
        }
        bool tag = false;
        for (int i = 1; i < n; ++i) {
          int k = 0;
          for (int j = i; j < n; ++j) {
            if (a[j][i] != 0) {
              k = j;
              break;
            }
          }
          if (i != k) {
            tag = !tag;
            std::swap(a[i], a[k]);
          }
          for (int j = i + 1; j < n; ++j) {
            long long t = 1ll * a[j][i] * Pow(a[i][i], mod - 2, mod) % mod;
            for (int k = i; k < n; ++k) {
              a[j][k] = static_cast<int>(mod - t * a[i][k] % mod + a[j][k]) % mod;
            }
          }
        }
        long long result = 1;
        for (int i = 1; i < n; ++i) {
          result = result * a[i][i] % mod;
        }
        if (tag) {
          result = mod - result;
        }
        return static_cast<int>(result);
      }
    };
    
    static constexpr int kMod = 1000000007;
    static constexpr int kNode = 12;
    static constexpr int kSampleNumber = 1024;
    
    struct Graph {
      std::vector<std::vector<bool>> g;
      int result;
    
      void Construct() {
        g.resize(kNode);
        for (int i = 0; i < kNode; ++i) {
          g[i].resize(kNode);
        }
        for (int i = 0; i < kNode; ++i) {
          for (int j = i + 1; j < kNode; ++j) {
            bool t = (std::rand() & 1) == 1;
            g[i][j] = g[j][i] = t;
          }
        }
        result = MSTCounter::Solver(g, kMod);
      }
      void GetResult(int n, int start, std::vector<int> *result) {
        for (int i = 0; i < kNode; ++i) {
          for (int j = i + 1; j < kNode; ++j) {
            if (g[i][j]) {
              int u = i + start;
              int v = j + start;
              result->push_back(u * n + v);
            }
          }
        }
      }
    };
    
    Graph graph[kSampleNumber];
    
    class InverseMatrixTree {
     public:
      std::vector<int> constructGraph(int r) {
        if (r == 0) {
          return {2};
        }
        std::srand(std::time(nullptr));
        for (int i = 0; i < kSampleNumber; ++i) {
          graph[i].Construct();
        }
        std::unordered_map<int, std::pair<int, int>> mapper;
        for (int i = 0; i < kSampleNumber; ++i) {
          for (int j = i; j < kSampleNumber; ++j) {
            int key =
                static_cast<int>(1ll * graph[i].result * graph[j].result % kMod);
            if (key != 0) {
              mapper[key] = {i, j};
            }
          }
        }
        for (const auto &e : mapper) {
          int key0 = e.first;
          int key1 = static_cast<int>(1ll * r *
                                      MSTCounter::Pow(key0, kMod - 2, kMod) % kMod);
          if (mapper.count(key1)) {
            int t[4] = {e.second.first, e.second.second, mapper[key1].first,
                        mapper[key1].second};
            int n = kNode * 4;
            std::vector<int> result = {n};
            for (int i = 0; i < 4; ++i) {
              graph[t[i]].GetResult(n, kNode * i, &result);
              if (i > 0) {
                int u = kNode * i;
                int v = u - 1;
                result.push_back(u * n + v);
              }
            }
            return result;
          }
        }
        return {};
      }
    };

    参考

    http://uoj.ac/problem/75

    http://vfleaking.blog.uoj.ac/blog/180

  • 相关阅读:
    JDK线程池原理之一:工作原理
    Hystrix Feign 特定状态码不熔断
    Hystrix熔断的方法级别(自定义commonKey)
    谨慎使用Exception
    FunctionalInterface~一个批量处理数据的类
    keycloak~账号密码认证和授权码认证
    keycloak~OIDC&OAuth2&自定义皮肤
    docker~添加hosts绑定的方法
    docker~产生的IP段与现有IP冲突问题
    高中数学知识要点及解题方法精粹[网摘]
  • 原文地址:https://www.cnblogs.com/jianglangcaijin/p/6950049.html
Copyright © 2020-2023  润新知