-
Notifications
You must be signed in to change notification settings - Fork 0
/
Build a Matrix With Conditions.cpp
67 lines (55 loc) · 2.04 KB
/
Build a Matrix With Conditions.cpp
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
class Solution {
public:
vector<vector<int>> buildMatrix(int k, vector<vector<int>>& rowConditions, vector<vector<int>>& colConditions) {
unordered_map<int, vector<int>> graph;
for (const auto& edge : rowConditions) {
graph[edge[0]].push_back(edge[1]);
}
vector<int> row_sorting = topo_sort(graph, k);
graph.clear();
for (const auto& edge : colConditions) {
graph[edge[0]].push_back(edge[1]);
}
vector<int> col_sorting = topo_sort(graph, k);
if (row_sorting.empty() || col_sorting.empty()) {
return {};
}
unordered_map<int, pair<int, int>> value_position;
for (int i = 0; i < k; ++i) {
value_position[row_sorting[i]].first = i;
value_position[col_sorting[i]].second = i;
}
vector<vector<int>> res(k, vector<int>(k, 0));
for (int value = 1; value <= k; ++value) {
int row = value_position[value].first;
int column = value_position[value].second;
res[row][column] = value;
}
return res;
}
private:
bool dfs(int src, unordered_map<int, vector<int>>& graph, unordered_set<int>& visited, unordered_set<int>& cur_path, vector<int>& res) {
if (cur_path.count(src)) return false;
if (visited.count(src)) return true;
visited.insert(src);
cur_path.insert(src);
for (int neighbor : graph[src]) {
if (!dfs(neighbor, graph, visited, cur_path, res)) // if any child returns false
return false;
}
cur_path.erase(src);
res.push_back(src);
return true;
}
vector<int> topo_sort(unordered_map<int, vector<int>>& graph, int k) {
unordered_set<int> visited;
unordered_set<int> cur_path;
vector<int> res;
for (int src = 1; src <= k; ++src) {
if (!dfs(src, graph, visited, cur_path, res))
return {};
}
reverse(res.begin(), res.end());
return res;
}
};