CodeVS1611_APIO2009_抢掠计划_C++

  题目:http://codevs.cn/problem/1611/

 

  关于题解请戳这里:http://www.cnblogs.com/hadilo/p/5892765.html

  下面给一个可以A的代码,由于没有无限栈只能用手写栈Tarjan,上面题解里给的代码是递归栈的Tarjan,会RE

  1 #include <cstdio>
  2 #include <algorithm>
  3 #include <cstring>
  4 #include <vector>
  5 #include <queue>
  6 #include <stack>
  7 #define nil 0
  8 #define N 500005
  9 using namespace std;
 10 
 11 int n, m, csh[N], S, P, f[N];
 12 int u[N << 2], v[N << 2], nxt[N << 2], pnt[N], e;
 13 int dfn[N], low[N], isin[N], hcash[N], tot, indx;
 14 bool instack[N], vis[N];
 15 int Sta[N], stop;
 16 vector <int> g[N];
 17 stack <int> s; 
 18 void add(int a, int b)
 19 {
 20     u[++e] = a; v[e] = b;
 21     nxt[e] = pnt[a]; pnt[a] = e;
 22 }
 23 void tarjan(int x)
 24 {
 25     s.push(x);
 26     dfn[x] = low[x] = ++indx;
 27     Sta[++stop] = x;
 28     instack[x] = true;
 29     while(!s.empty())
 30     {
 31         int t = s.top();
 32         for(int i = pnt[t]; i != nil; i = nxt[i])
 33         {
 34             if(dfn[v[i]] == 0)
 35             {
 36                 dfn[v[i]] = low[v[i]] = ++indx;
 37                 Sta[++stop] = v[i]; instack[v[i]] = true;
 38                 s.push(v[i]);
 39                 break;
 40             }
 41         }
 42         if(t == s.top())
 43         {
 44             for(int i = pnt[t]; i != nil; i = nxt[i])
 45             {
 46                 if(dfn[v[i]] > dfn[t]) low[t] = min(low[t], low[v[i]]);
 47                 else if(instack[v[i]]) low[t] = min(low[t], dfn[v[i]]);
 48             }
 49             if(dfn[t] == low[t])
 50             {
 51                 ++tot;
 52                 int j;
 53                 do
 54                 {
 55                     j = Sta[stop--];
 56                     instack[j] = false;
 57                     isin[j] = tot;
 58                     hcash[tot] += csh[j];
 59                 } while(j != t);
 60             }
 61             s.pop();
 62         }
 63     }
 64 }
 65 void init()
 66 {
 67     int a, b;
 68     scanf("%d%d", &n, &m);
 69     for(int i = 1; i <= m; ++i)
 70     {
 71         scanf("%d%d", &a, &b);
 72         add(a, b);
 73     }
 74     for(int i = 1; i <= n; ++i)
 75     {
 76         scanf("%d", &csh[i]);
 77     }
 78     scanf("%d%d", &S, &P);
 79     for(int i = 1; i <= n; ++i)
 80     {
 81         if(dfn[i] == 0)
 82         {
 83             tarjan(i);
 84         }
 85     }
 86     for(int i = 1; i <= n; ++i)
 87     {
 88         for(int j = pnt[i]; j != nil; j = nxt[j])
 89         {
 90             if(isin[i] != isin[v[j]])
 91             {
 92                 g[isin[i]].push_back(isin[v[j]]);
 93             }
 94         }
 95     }
 96 }
 97 void work()
 98 {
 99     queue <int> Q;
100     memset(vis, 0, sizeof(vis));
101     memset(f, 0, sizeof(f));
102     f[isin[S]] = hcash[isin[S]];
103     Q.push(isin[S]);
104     vis[isin[S]] = true;
105     while(!Q.empty())
106     {
107         int t = Q.front();
108         Q.pop();
109         vis[t] = false;
110         for(int i = 0; i < g[t].size(); ++i)
111         {
112             if(f[g[t][i]] < f[t] + hcash[g[t][i]])
113             {
114                 f[g[t][i]] = f[t] + hcash[g[t][i]];
115                 if(!vis[g[t][i]])
116                 {
117                     vis[g[t][i]] = true;
118                     Q.push(g[t][i]);
119                 }
120             }
121         }
122     }
123     int ans = 0, a;
124     for(int i = 1; i <= P; ++i)
125     {
126         scanf("%d", &a);
127         ans = max(ans, f[isin[a]]);
128     }
129     printf("%d\n", ans);
130 }
131 int main()
132 {
133     init();
134     work();
135     return 0;
136 }

 

 

 

版权所有,转载请联系作者,违者必究

QQ:740929894

posted @ 2016-09-21 15:27  Hadilo  阅读(530)  评论(0编辑  收藏  举报