ACM 实验室2020.10.10天梯赛练习*2
7-15 球队“食物链”
题意:n个点m个关系,要求一个排列使得满足关系
思路:dfs+剪枝,注意两个剪枝点:
1.如果有解第一个数一定是1
2.dfs中如果剩下的点中没有能和1相连通的,就不用遍历了
#include <bits/stdc++.h> using namespace std; typedef long long ll; typedef pair<int, int> PII; const int maxn = 100 + 15; const double eps = 1e-9; int mp[maxn][maxn]; int n; int vis[maxn]; bool findYes; vector<int> v; void dfs(int now) { bool flag = true; for (int i = 1; i <= n; i++) if (!vis[i]) { flag = false; break; } if (flag) { if (!mp[v[v.size() - 1]][v[0]]) { return; } for (int i = 0; i < v.size() - 1; i++) cout << v[i] << " "; cout << v[v.size() - 1] << endl; findYes = true; return; } bool yes = false; for (int i = 1; i <= n; i++) if (!vis[i] && mp[i][1]) { yes = true; } if (!yes) return; for (int i = 1; i <= n; i++) { if (!vis[i] && mp[now][i]) { vis[i] = true; v.push_back(i); dfs(i); if (findYes) return; v.pop_back(); vis[i] = false; } } } int main() { cin >> n; for (int i = 1; i <= n; i++) { string s; cin >> s; for (int j = 0; j < n; j++) { if (s[j] == 'W') mp[i][j + 1] = 1; else if (s[j] == 'L') mp[j + 1][i] = 1; } } vis[1] = true; v.push_back(1); dfs(1); if (!findYes) cout << "No Solution" << endl; return 0; }