JD18. 有序图
描述
输入描述
第一行包含两个正整数n,m,分别表示图上结点是数量和有向边的数量。 接下来m行每行有两个正整数u,v,表示存在一条从u结点到v结点的有向边。输出描述
输出一个字典序最小的,1-n的全排列,使得这张图是有序图,元素中间使用空格隔开。示例1
输入:
3 3 1 2 1 3 3 2
输出:
1 3 2
C++14 解法, 执行用时: 47ms, 内存消耗: 8420KB, 提交时间: 2020-07-28
#include<iostream> #include<vector> #include<queue> using namespace std; vector<int> solve(vector<vector<int>> &adj, vector<int> &in, int n) { priority_queue<int> q; vector<int> ret(n+1); int cnt = n; for (int i=1; i<=n; i++) if (in[i]==0) q.push(i); while (!q.empty()) { int t = q.top(); q.pop(); ret[t] = cnt--; for (int i=0; i<adj[t].size(); i++) if (--in[adj[t][i]]==0) q.push(adj[t][i]); } return ret; } int main() { ios::sync_with_stdio(false); cin.tie(0); int n, k; cin >> n >> k; vector<vector<int>> adj(n+1); vector<int> in(n+1, 0); for (int i=0; i<k; i++) { int u, v; cin >> u >> v; adj[v].push_back(u); in[u]++; } vector<int> ret = solve(adj, in, n); for (int i=1; i<=n; i++) cout << ret[i] << " "; return 0; }
C++ 解法, 执行用时: 49ms, 内存消耗: 7196KB, 提交时间: 2020-10-29
#include<iostream> #include<vector> #include<queue> using namespace std; vector<int> solve(vector<vector<int>> &adj, vector<int> &in, int n) { priority_queue<int> q; vector<int> ret(n+1); int cnt = n; for (int i=1; i<=n; i++) if (in[i]==0) q.push(i); while (!q.empty()) { int t = q.top(); q.pop(); ret[t] = cnt--; for (int i=0; i<adj[t].size(); i++) if (--in[adj[t][i]]==0) q.push(adj[t][i]); } return ret; } int main() { ios::sync_with_stdio(false); cin.tie(0); int n, k; cin >> n >> k; vector<vector<int>> adj(n+1); vector<int> in(n+1, 0); for (int i=0; i<k; i++) { int u, v; cin >> u >> v; adj[v].push_back(u); in[u]++; } vector<int> ret = solve(adj, in, n); for (int i=1; i<=n; i++) cout << ret[i] << " "; return 0; }