[Apio2009]Atm
Posted NWU_ACM
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了[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 }
以上是关于[Apio2009]Atm的主要内容,如果未能解决你的问题,请参考以下文章