zoukankan      html  css  js  c++  java
  • 图论.连通性专题

    开一个关于图的连通性的专题,内容包括:

    • 无向图的割点、桥、双连通分量
    • 有向图的强连通分量
    • 最大团
    • 极大团
    • 全局最小割
    • 最短路相关

    Introduction to Algorithms 3rd edition, page 621,

    Problem 22-2 Articulation points, bridges, and biconnected components

    Let $G = (V, E)$ be a connected, undirected graph. An articulation point of $G$ is a vertex whose removal disconnects $G$. A bridge of $G$ is an edge whose removal disconnects $G$. A biconnected component of $G$ is a maximal set of edges such that any two edges in the set lie on a common simple cycle. Figure 22.10 illustrates these definitions.

    We can determine articulation points, bridges, and biconnected components using depth-first search. Let $G_{pi} = (V, E_{pi})$ be a depth-first tree of $G$.
    a. Prove that the root of $G_{pi}$ is an articulation point of $G$ if and only if it has at least two children in $G_{pi}$.
    b. Let $v$ be a nonroot vertex of $G_{pi}$. Prove that $v$ is an articulation point of $G$ if and only if $v$ has a child $s$ such that there is no back edge from $s$ or any descendant of $s$ to a proper ancestor of $v$.
    c. Let
    egin{aligned}
    v.low = min
    egin{cases}
    v.d, \
    w.d : ext{$(u, w)$ is a back edge for some descendant $u$ of $v$}.
    end{cases}
    end{aligned}
    Show how to compute $v.low$ for all vertices $vin V$ in $O(E)$ time.
    d. Show how to compute all articulation points in $O(E)$ time.
    e. Prove that an edge of $G$ is a bridge if and only if it does not lie on any simple cycle of $G$.
    f. Show how to compute all the bridges of $G$ in $O(E)$ time.
    g. Prove that the biconnected components of $G$ partition the nonbridge edges of $G$.
    h. Give an $O(E)$-time algorithm to label each edge $e$ of $G$ with a positive integer $e.bcc$ such that $e.bcc = e'.bcc$ if and only if $e$ and $e'$ are in the same biconnected component.

    Problem 22-3 Euler tour

    An Euler tour of a strongly connected, directed graph $G = (V, E)$ is a cycle that traverses each edge of $G$ exactly once, although it may visit a vertex more than once.
    a. Show that $G$ has an Euler tour if and only if in-degree($v$) = out-degree($v$) for each vertex $vin V$.
    b. Describe an $O(E)$-time algorithm to find an Euler tour of $G$ if one exists. (Hint: Merge edge-disjoint-cycles.)

    Problem 22.5-7

    A directed graph $G = (V, E)$ is semiconnected if, for all pairs of vertices $u, vin V$, we have $u leadsto v$ or $v leadsto u$. Give an efficient algorithm to determine whether or not $G$ is semiconnected. Prove that your algorithm is correct, and analyze its running time.

    求 $G$ 的强连通分量,缩点后得到一个 DAG。问题可归约为求这个 DAG 是否为 semiconnected。一个 DAG 是 semiconnected 当且仅当其中有一个生成子图是一条链,换言之,设 DAG 中有 $n$ 个节点,这些节点按拓扑序依次是 $v_1, v_2, dots, v_n$,对于每个 $i =1, 2, 3, dots, n - 1$,要有一条从 $v_i$ 到 $v_{i+1}$ 的有向边。
    至于代码实现,以 Tarjan 的强连通分量算法为例,我们可以在 DFS 的过程中,对于每个点 $u$ 计算出从 $u$ 出发的边所能到达的其他强连通分量的编号的最大值。

      SCC(int n, const Graph &g,
          function<int(const Arc &e)> get_v = [](const Arc &e) { return e; })
          : n(n),
            g(g),
            get_v(move(get_v)),
            scc_id(n + 1, -1),
            scc_cnt(0) {}  // SCCs are indexed from 0
      bool dfs(int u) {
        static int time;
        static stack<int> s;
        static vector<int> low(n + 1), order(n + 1);
        static vector<bool> in_stack(n + 1);
        static vector<int> max_scc_id(n + 1, -1);
        order[u] = low[u] = ++time;
        s.push(u);
        in_stack[u] = true;
    
        for (auto &e : g[u]) {
          int v = get_v(e);
          if (!order[v]) {
            if (!dfs(v)) {
              return false;
            }
            low[u] = min(low[u], low[v]);
          } else if (in_stack[v]) {
            low[u] = min(low[u], order[v]);
          }
          if (!in_stack[v]) {
            max_scc_id[u] = max(max_scc_id[u], scc_id[v]);
          }
        }
        int max_scc_ID = -1;
        if (order[u] == low[u]) {
          while (true) {
            int v = s.top();
            s.pop();
            in_stack[v] = false;
            scc_id[v] = scc_cnt;
            max_scc_ID = max(max_scc_ID, max_scc_id[v]);
            if (u == v) break;
          }
          if (max_scc_ID != scc_cnt - 1) {
            return false;
          }
          ++scc_cnt;
        }
        return true;
      }
    };
    
  • 相关阅读:
    CSS3:三个矩形,一个宽200px,其余宽相等且自适应满铺
    pidera安装node.js(树莓派)
    深入JavaScript模块化编程
    c# 多显示器设置主屏幕(Set primary screen for multiple monitors)
    c# 获取移动硬盘信息、监听移动设备的弹出与插入事件
    C# 弹出USB外接硬盘(U盘)
    log4net 自定义Appender
    Scrum 思考
    监控浏览器关闭事件
    判断地图的点是否在面内 腾讯地图
  • 原文地址:https://www.cnblogs.com/Patt/p/6001434.html
Copyright © 2011-2022 走看看