#include <cstdio> #include <algorithm> #include <vector> using namespace std; const int MAXN = 2E5, MAXSEQ = 2E5, MAXPAIR = 5E5; vector<int> seq[MAXSEQ+5]; pair<int, int> para[MAXPAIR+5]; struct VERTEX { vector<int> pair_num; vector<int> edge; int curr_name, p, qt, tree_num; bool vis; }; VERTEX fio[MAXN+MAXSEQ+5]; int seq_qt, n, pair_qt; long long result; int find(int x) { if(fio[x].p!=x) fio[x].p=find(fio[x].p); return fio[x].p; } void union_set(int x, int y) { x=find(x); y=find(y); if(x>y) fio[y].p=x; else fio[x].p=y; } void DFS(int curr, int prev, int tree_num) { int partner; fio[curr].vis=true; fio[curr].tree_num = tree_num; for(vector<int>::iterator it = fio[curr].pair_num.begin(); it!=fio[curr].pair_num.end(); ++it) { if (para[*it].first == curr) partner = para[*it].second; else partner = para[*it].first; if(fio[partner].vis == true && fio[curr].tree_num == fio[partner].tree_num) seq[find(partner) - n].push_back(*it); } for(vector<int>::iterator it = fio[curr].edge.begin(); it!=fio[curr].edge.end(); ++it) DFS(*it, curr, tree_num); union_set(curr, prev); } int main() { scanf("%d%d%d", &n, &seq_qt, &pair_qt); for(int i=1; i<=n; ++i) { scanf("%d", &(fio[i].qt)); fio[i].p = i; fio[i].curr_name = i; } for(int i=1; i<=seq_qt; ++i) { int a, b; scanf("%d%d", &a, &b); fio[i+n].edge.push_back(fio[a].curr_name); fio[i+n].edge.push_back(fio[b].curr_name); fio[a].curr_name = i+n; fio[b].curr_name = i+n; fio[i+n].p = i+n; } for(int i=1; i<=pair_qt; i++) { int a, b; scanf("%d%d", &a, &b); para[i]=make_pair(a, b); fio[a].pair_num.push_back(i); fio[b].pair_num.push_back(i); } for(int i=seq_qt; i>0; --i) { if(!fio[n+i].vis)DFS(n+i, 0, i); } for(int i=1; i<=seq_qt; ++i) { sort(seq[i].begin(), seq[i].end()); for(vector<int>::iterator it=seq[i].begin(); it!=seq[i].end(); ++it) { int mini; mini = min(fio[para[*it].first].qt, fio[para[*it].second].qt); fio[para[*it].first].qt -= mini; fio[para[*it].second].qt -= mini; result += mini; } } result *= 2LL; printf("%lld\n", result); return 0; }
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 | #include <cstdio> #include <algorithm> #include <vector> using namespace std; const int MAXN = 2E5, MAXSEQ = 2E5, MAXPAIR = 5E5; vector<int> seq[MAXSEQ+5]; pair<int, int> para[MAXPAIR+5]; struct VERTEX { vector<int> pair_num; vector<int> edge; int curr_name, p, qt, tree_num; bool vis; }; VERTEX fio[MAXN+MAXSEQ+5]; int seq_qt, n, pair_qt; long long result; int find(int x) { if(fio[x].p!=x) fio[x].p=find(fio[x].p); return fio[x].p; } void union_set(int x, int y) { x=find(x); y=find(y); if(x>y) fio[y].p=x; else fio[x].p=y; } void DFS(int curr, int prev, int tree_num) { int partner; fio[curr].vis=true; fio[curr].tree_num = tree_num; for(vector<int>::iterator it = fio[curr].pair_num.begin(); it!=fio[curr].pair_num.end(); ++it) { if (para[*it].first == curr) partner = para[*it].second; else partner = para[*it].first; if(fio[partner].vis == true && fio[curr].tree_num == fio[partner].tree_num) seq[find(partner) - n].push_back(*it); } for(vector<int>::iterator it = fio[curr].edge.begin(); it!=fio[curr].edge.end(); ++it) DFS(*it, curr, tree_num); union_set(curr, prev); } int main() { scanf("%d%d%d", &n, &seq_qt, &pair_qt); for(int i=1; i<=n; ++i) { scanf("%d", &(fio[i].qt)); fio[i].p = i; fio[i].curr_name = i; } for(int i=1; i<=seq_qt; ++i) { int a, b; scanf("%d%d", &a, &b); fio[i+n].edge.push_back(fio[a].curr_name); fio[i+n].edge.push_back(fio[b].curr_name); fio[a].curr_name = i+n; fio[b].curr_name = i+n; fio[i+n].p = i+n; } for(int i=1; i<=pair_qt; i++) { int a, b; scanf("%d%d", &a, &b); para[i]=make_pair(a, b); fio[a].pair_num.push_back(i); fio[b].pair_num.push_back(i); } for(int i=seq_qt; i>0; --i) { if(!fio[n+i].vis)DFS(n+i, 0, i); } for(int i=1; i<=seq_qt; ++i) { sort(seq[i].begin(), seq[i].end()); for(vector<int>::iterator it=seq[i].begin(); it!=seq[i].end(); ++it) { int mini; mini = min(fio[para[*it].first].qt, fio[para[*it].second].qt); fio[para[*it].first].qt -= mini; fio[para[*it].second].qt -= mini; result += mini; } } result *= 2LL; printf("%lld\n", result); return 0; } |