首页 > 代码库 > [Apio2009]Atm

[Apio2009]Atm

技术分享
  1 #include<cstdio>
  2 #include<cstring>
  3 #include<iostream>
  4 #include<string>
  5 #include<vector>
  6 #include<queue>
  7 #include<stack>
  8 #include<set>
  9 #include<algorithm>
 10 using namespace std;
 11 #define N 500001
 12 stack<int>Sta;
 13 queue<int>Que;
 14 struct edge
 15 {
 16     int u,v,next;
 17 }edge1[N],edge2[N];
 18 bool isBar[N],inStack[N];
 19 int low[N],dfn[N],belong[N],money[N],newMoney[N],cnt,Time,start;
 20 int maxMoney[N],head[N],head2[N];
 21  
 22 void add(int u, int v, int id)
 23 {
 24     edge1[id].u = u;
 25     edge1[id].v = v;
 26     edge1[id].next = head[u];
 27     head[u] = id;
 28 }
 29  
 30 void add2(int u, int v, int id)
 31 {
 32     edge2[id].u = u;
 33     edge2[id].v = v;
 34     edge2[id].next = head2[u];
 35     head2[u] = id;
 36 }
 37 void Tarjan(int s)
 38 {
 39     dfn[s] = low[s] = ++Time;
 40     Sta.push(s);
 41     inStack[s] = true;
 42     for(int u = head[s]; ~u; u = edge1[u].next)
 43     {
 44         int v = edge1[u].v;
 45         if(dfn[v] == 0){
 46             Tarjan(v);
 47             low[s] = min(low[s], low[v]);
 48         }
 49         else if(inStack[v] == true){
 50             low[s] = min(low[s], dfn[v]);
 51         }
 52     }
 53     if(dfn[s] == low[s])
 54         {
 55             cnt ++;
 56             while(!Sta.empty()){
 57               int temp = Sta.top(); Sta.pop();
 58               belong[temp] = cnt;
 59               newMoney[cnt] += money[temp];
 60               inStack[temp] = false;
 61               if(temp == s) break;
 62             }
 63         }
 64 }
 65  
 66 int spfa()
 67 {
 68     int ans = 0;
 69     Que.push(start);
 70     memset(maxMoney,0,sizeof(maxMoney));
 71     maxMoney[start] = newMoney[start];
 72     while(!Que.empty())
 73     {
 74         int now = Que.front(); Que.pop();
 75         for(int u = head2[now]; ~u; u = edge2[u].next)
 76         {
 77             int v = edge2[u].v;
 78             if(maxMoney[now] + newMoney[v] > maxMoney[v])
 79             {
 80                 maxMoney[v] = maxMoney[now] + newMoney[v];
 81                 Que.push(v);
 82             }
 83             if(isBar[v]) ans = max(ans, maxMoney[v]);
 84         }
 85     }
 86     return ans;
 87 }
 88  
 89 int main()
 90 {
 91     int n,m,a,b,s,p;
 92     scanf("%d%d",&n,&m);
 93     memset(head,-1,sizeof(head));
 94     for (int i = 0; i < m; i++) {
 95       /* code */
 96       scanf("%d%d",&a, &b);
 97       add(a,b,i+1);
 98     }
 99     for (int i = 1; i <= n; i++) {
100       /* code */
101       scanf("%d",&money[i]);
102     }
103     scanf("%d%d",&s,&p);
104     memset(inStack,false,sizeof(inStack));
105     memset(newMoney,0,sizeof(newMoney));
106     memset(isBar,false,sizeof(isBar));
107     memset(dfn,0,sizeof(dfn));
108     cnt = Time = 0;
109     for(int i = 1; i <= n; i++) if(dfn[i] == 0) Tarjan(i);
110     if(cnt == 1) {printf("%d",newMoney[cnt]);return 0;}
111     for(int i=0;i<p;i++)
112     {
113       scanf("%d", &a);
114       isBar[belong[a]] = true;
115     }
116     start = belong[s];
117     memset(head2,-1,sizeof(head2));
118     int kkk = 0;
119     for(int i =1; i <= n; i ++)
120     {
121         for(int u = head[i]; ~u; u = edge1[u].next){
122             int v = edge1[u].v;
123             if(belong[i] != belong[v]){
124                 add2(belong[i],belong[v],++kkk);
125             }
126         }
127     }
128  
129     int ans = spfa();
130     printf("%d", ans);
131 }
View Code

 

[Apio2009]Atm