16 #include "llvm/ADT/DenseMap.h"
17 #include "llvm/ADT/DenseSet.h"
18 #include "llvm/ADT/SmallVector.h"
32 cycle.push_back(node);
33 node = parents.lookup(node);
34 assert(node &&
"got an empty value in the cycle");
35 }
while (node != rep);
52 Value rep = cycle.front();
57 for (
auto outer = graph.begin(), e = graph.end(); outer != e; ++outer) {
58 Value target = outer->first;
59 if (cycleSet.contains(target)) {
61 unsigned parentDepth = parentDepths.lookup(target);
62 for (
const auto &inner : outer->second) {
63 Value source = inner.first;
65 if (cycleSet.contains(source))
69 std::pair<unsigned, unsigned> cost = inner.second.cost;
70 assert(parentDepth <= cost.first &&
"invalid parent depth");
77 cost.first -= parentDepth;
78 auto it = repEntries.find(source);
79 if (it == repEntries.end() || it->second.cost > cost) {
80 actualTarget[source] = target;
83 repEntries[source].cost = cost;
92 std::pair<unsigned, unsigned> bestCost;
93 auto inner = entries.begin(), innerE = entries.end();
94 while (inner != innerE) {
95 Value source = inner->first;
96 if (cycleSet.contains(source)) {
98 if (!bestSource || bestCost > inner->second.cost) {
100 bestCost = inner->second.cost;
102 entries.erase(inner++);
110 entries[rep].cost = bestCost;
111 actualSource[target] = bestSource;
117 graph[rep] = std::move(repEntries);
121 : graph(std::move(graph)), root(root) {}
126 parents[root] =
Value();
127 unsigned totalCost = 0;
132 parentDepths.reserve(graph.size());
137 for (
const auto &outer : graph) {
138 Value node = outer.first;
139 if (parents.count(node))
145 parentDepths.clear();
147 auto it = graph.find(node);
148 assert(it != graph.end() &&
"the graph is not strongly connected");
152 Value &bestSource = parents[node];
153 std::pair<unsigned, unsigned> bestCost;
154 for (
const auto &inner : it->second) {
156 if (!bestSource || bestCost > entry.
cost) {
157 bestSource = inner.first;
158 bestCost = entry.
cost;
161 assert(bestSource &&
"the graph is not strongly connected");
162 parentDepths[node] = bestCost.first;
164 totalCost += bestCost.first;
165 }
while (!parents.count(node));
168 if (parentDepths.count(node)) {
177 contract(graph, cycle, parentDepths, actualSource, actualTarget);
181 for (
auto &p : parents)
182 if (p.second == node)
185 p.second = actualSource.lookup(p.first);
188 Value parent = parents.lookup(node);
189 Value entry = actualTarget.lookup(parent);
190 cycle.push_back(node);
191 for (
size_t i = 0, e = cycle.size() - 1; i < e; ++i) {
192 totalCost += parentDepths.lookup(cycle[i]);
193 if (cycle[i] == entry)
194 parents[cycle[i]] = parent;
196 parents[cycle[i]] = cycle[i + 1];
211 for (
Value node : nodes) {
213 Value parent = parents.lookup(node);
214 assert(parent &&
"invalid parent");
215 children[parent].push_back(node);
221 result.reserve(nodes.size());
222 result.emplace_back(root,
Value());
225 for (
size_t i = 0; i < result.size(); ++i) {
226 Value node = result[i].first;
227 for (
Value child : children[node])
228 result.emplace_back(child, node);
static void contract(RootOrderingGraph &graph, ArrayRef< Value > cycle, const DenseMap< Value, unsigned > &parentDepths, DenseMap< Value, Value > &actualSource, DenseMap< Value, Value > &actualTarget)
Contracts the specified cycle in the given graph in-place.
static SmallVector< Value > getCycle(const DenseMap< Value, Value > &parents, Value rep)
Returns the cycle implied by the specified parent relation, starting at the given node.
This class represents an instance of an SSA value in the MLIR system, representing a computable value...
unsigned solve()
Runs the Edmonds' algorithm for the current graph, returning the total cost of the minimum-weight spa...
std::vector< std::pair< Value, Value > > EdgeList
A list of edges (child, parent).
OptimalBranching(RootOrderingGraph graph, Value root)
Constructs the solver for the given graph and root value.
EdgeList preOrderTraversal(ArrayRef< Value > nodes) const
Returns the computed edges as visited in the preorder traversal.
Include the generated interface declarations.
The information associated with an edge in the cost graph.
std::pair< unsigned, unsigned > cost
The depth of the connector Value w.r.t.