zoukankan      html  css  js  c++  java
  • POJ1094——拓扑排序和它的唯一性

    比较模板的topological-sort题,关键在于每个元素都严格存在唯一的大小关系,而一般的拓扑排序只给出一个可能解,这就需要每趟排序的过程中监视它是不是总坚持一条唯一的路径。

    算法导论里面的拓扑排序运用的是DFS the DAG,记录每个顶点的进入时间和离开时间,根据其先后插入单链表的做法。而我认为一种方法是更直观的,就是维护一个入度为0的顶点集合(我用的队列其实没差),每次对其中一个加入结果序列——同时删除它的所有出边——更新其他点的入度的做法,在我的算法数据结构实现模板里有正确实现https://github.com/jily16/ACMCodes(打广告

    在判断拓扑排序结果唯一性时这种方法也表现出了一个优势,每次访问0入度集合时查看大小,当元素多于1的时候可行的选择就出现了分歧——即可判定此DAG的拓扑排序不唯一(当然本题的信息在不断更新,所以不能立刻判死)。

    AC代码:

      1 #include <vector>
      2 #include <iostream>
      3 #include <queue>
      4 using namespace std;
      5 //POJ1094
      6 int const INF = 0x3f3f3f3f;
      7 //返回空数组说明暂时不行
      8 //cyclic说明矛盾
      9 vector<int> ts(vector<vector<int> > const &g, bool &cyclic)
     10 {
     11     int n = g.size();
     12     vector<int> d(n);
     13     for (int i = 0; i < n; ++i)
     14     {
     15         for (int j = 0; j < n; ++j)
     16         {
     17             if (g[i][j] < INF)
     18             {
     19                 ++d[j];
     20             }
     21         }
     22     }
     23     queue<int> q;
     24     for (int i = 0; i < n; ++i) if (d[i] == 0) q.push(i);
     25     int d0;
     26     int tot = 0;
     27     bool not_unique = false;
     28     vector<int> ans;
     29     while (!q.empty())
     30     {
     31         if (q.size() > 1)
     32         {
     33             not_unique = true;    //解不唯一
     34         }
     35         d0 = q.front();
     36         q.pop();
     37         ans.push_back(d0);
     38         ++tot;
     39         for (int i = 0; i < n; ++i)
     40         {
     41             if (d[i] != 0 && g[d0][i] < INF)
     42             {
     43                 --d[i];
     44                 if (d[i] == 0)
     45                 {
     46                     q.push(i);
     47                 }
     48             }
     49         }
     50     }
     51     if (tot != n) cyclic = true;
     52     if (not_unique) return vector<int>();
     53     else return ans;
     54 }
     55 int main()
     56 {
     57     int n, m;
     58     while (cin >> n >> m && n && m)
     59     {
     60         bool done = false;
     61         vector<vector<int> > g;
     62         char alp1, alp2;
     63         char lessthan;
     64         int num1, num2;
     65         for (int i = 0; i < m; ++i)
     66         {
     67             cin >> alp1 >> lessthan >> alp2;
     68             if (done) continue;
     69             num1 = alp1 - 'A';
     70             num2 = alp2 - 'A';
     71             int bignum = max(num1, num2);
     72             //extend the graph
     73             if (g.size() < bignum + 1)
     74             {
     75                 int ori_size = g.size();
     76                 for (int i = 0; i < ori_size; ++i)
     77                 {
     78                     for (int j = 0; j < bignum + 1 - ori_size; ++j)
     79                     {
     80                         g[i].push_back(INF);
     81                     }
     82                 }
     83                 for (int i = 0; i < bignum + 1 - ori_size; ++i)
     84                 {
     85                     g.push_back(vector<int>(bignum + 1, INF));
     86                 }
     87             }
     88             g[num1][num2] = 1;
     89             //judge from here
     90             bool cycle = false;
     91             if (g.size() < n)
     92             {
     93                 ts(g, cycle);
     94                 if (cycle)
     95                 {
     96                     cout << "Inconsistency found after " << i + 1 << " relations.
    ";
     97                     done = true;
     98                 }
     99                 else
    100                 {
    101                     if (i == m - 1)
    102                     {
    103                         cout << "Sorted sequence cannot be determined.
    ";
    104                         done = true;
    105                     }
    106                 }
    107             }
    108             else
    109             {
    110                 vector<int> ans = ts(g, cycle);
    111                 if (cycle)
    112                 {
    113                     cout << "Inconsistency found after " << i + 1 << " relations.
    ";
    114                     done = true;
    115                 }
    116                 else
    117                 {
    118                     if (ans.size() != 0)
    119                     {
    120                             cout << "Sorted sequence determined after " << i + 1 << " relations: ";
    121                             for (int i = 0; i < n; ++i) cout << (char)(ans[i] + 'A');
    122                             cout << ".
    ";
    123                             done = true;
    124                     }
    125                     else
    126                     {
    127                         if (i < m - 1) continue;
    128                         else
    129                         {
    130                             cout << "Sorted sequence cannot be determined.
    ";
    131                             done = true;
    132                         }
    133                     }
    134                 }
    135             }
    136         }
    137     }
    138     return 0;
    139 }
  • 相关阅读:
    激活Maven profile的几种方式
    利用maven的filter和profile实现不同环境使用不同的配制
    通过profile 用maven命令打不同配置的变量包
    使用Maven Profile实现多环境构建
    Window下Nexus私服搭建
    linux之nginx
    linux之命令进阶
    linux之常见命令
    flask中路由的本质源码分析
    vmware+CentOs 6.9的安装步骤
  • 原文地址:https://www.cnblogs.com/jily/p/6500555.html
Copyright © 2011-2022 走看看