拓扑排序——有向无环图(湖南省第十二届大学生计算机程序设计竞赛 B)
2016-09-04 12:46
411 查看
题目链接:
http://acm.csu.edu.cn/OnlineJudge/problem.php?id=1804
分析:
给出n个点和m条边,然后给出长度为n的两个数组a[]和b[],给出m条有向边u->v,求下面表达式的值
题解:
看到有向无环图(DAG),我们很容易就想到了拓扑排序,如果c点被b点指向,那么指向b点的a也能抵达c,所以我们把整个图按照拓扑排序倒序遍历一次,每次计算能抵达当前点j的点i:w[i] = w[i] + w[j] + b[j]。最后再给每一个w[i]乘上a[i]即可。
AC代码:
http://acm.csu.edu.cn/OnlineJudge/problem.php?id=1804
分析:
给出n个点和m条边,然后给出长度为n的两个数组a[]和b[],给出m条有向边u->v,求下面表达式的值
题解:
看到有向无环图(DAG),我们很容易就想到了拓扑排序,如果c点被b点指向,那么指向b点的a也能抵达c,所以我们把整个图按照拓扑排序倒序遍历一次,每次计算能抵达当前点j的点i:w[i] = w[i] + w[j] + b[j]。最后再给每一个w[i]乘上a[i]即可。
AC代码:
/************************************************************************* > File Name: test.cpp > Author: Akira > Mail: qaq.febr2.qaq@gmail.com ************************************************************************/ #include <iostream> #include <cstdio> #include <cstring> #include <string> #include <cstdlib> #include <algorithm> #include <queue> #include <stack> #include <map> #include <cmath> #include <vector> #include <set> #include <list> #include <ctime> typedef long long LL; typedef unsigned long long ULL; typedef long double LD; #define MST(a,b) memset(a,b,sizeof(a)) #define CLR(a) MST(a,0) #define Sqr(a) ((a)*(a)) using namespace std; #define MaxN 100010 #define MaxM MaxN*10 #define INF 0x3f3f3f3f #define bug cout<<88888888<<endl; const int mod = 1000000007; int n,m; LL a[MaxN], b[MaxN]; LL w[MaxN]; int Out[MaxN]; vector<int> vec[MaxN]; priority_queue <int , vector<int>, greater<int> >Q; void init() { CLR(w); CLR(Out); for(int i=1;i<=n;i++) vec[i].clear(); } int main() { while(~scanf("%d%d", &n, &m)) { init(); for(int i=1;i<=n;i++) { scanf("%lld%lld", &a[i], &b[i]); } int u,v; for(int i=0;i<m;i++) { scanf("%d%d", &u, &v); vec[v].push_back(u); Out[u]++; } while(!Q.empty()) Q.pop(); for(int i=1;i<=n;i++) { if(Out[i] == 0) { Q.push(i); w[i] = 0; } } while(!Q.empty()) { int tmp = Q.top(); Q.pop(); for(int i=0;i<vec[tmp].size();i++) { int to = vec[tmp][i]; Out[to]--; if(Out[to] == 0) Q.push(to); w[to] += w[tmp]; w[to]%=mod; w[to] += b[tmp]; w[to]%=mod; } } LL ans = 0; for(int i=1;i<=n;i++) { ans += w[i]*a[i]; ans%=mod; } cout << ans << endl; } //system("pause"); }
相关文章推荐
- 湖南省第十二届大学生计算机程序设计竞赛 problem A 2016
- CSU1801(第十二届湖南省大学生计算机程序设计竞赛(热身赛)- D)
- 【最短路】【数学】CSU 1806 Toll (2016湖南省第十二届大学生计算机程序设计竞赛)
- CSU 1809 Parenthesis【湖南省第十二届大学生计算机程序设计竞赛 G题】
- 湖南省第十二届大学生计算机程序设计竞赛 2016
- 2016年湖南省第十二届大学生计算机程序设计竞赛:A—2016
- 【模拟】【数学】CSU 1803 2016 (2016湖南省第十二届大学生计算机程序设计竞赛)
- 【最短路】【数学】CSU 1806 Toll (2016湖南省第十二届大学生计算机程序设计竞赛)
- 2016年湖南省第十二届大学生计算机程序设计竞赛:B—有向无环图
- 2016年湖南省第十二届大学生计算机程序设计竞赛:F—地铁
- CSU 1809 Parenthesis (线段树)【2016年湖南省第十二届大学生计算机程序设计竞赛 - G】
- 【模拟】【数学】CSU 1803 2016 (2016湖南省第十二届大学生计算机程序设计竞赛)
- 2016年湖南省第十二届大学生计算机程序设计竞赛 - G CSU 1809 Parenthesis (线段树)
- 2016年湖南省第十二届大学生计算机程序设计竞赛 A. 2016(数学)
- 【贪心】CSU 1809 Parenthesis (2016湖南省第十二届大学生计算机程序设计竞赛)
- 【模拟】CSU 1807 最长上升子序列~ (2016湖南省第十二届大学生计算机程序设计竞赛)
- 湖南省第十二届大学生计算机程序设计竞赛 A 2016
- 湖南省第十二届大学生计算机程序设计竞赛 B 有向无环图 拓扑DP
- 2016年湖南省第十二届大学生计算机程序设计竞赛
- 【贪心】CSU 1809 Parenthesis (2016湖南省第十二届大学生计算机程序设计竞赛)