feat(ir): rethink logic for finding vertices with no inputs
This commit is contained in:
parent
66639771ac
commit
4fd35736d5
1 changed files with 15 additions and 21 deletions
|
@ -191,7 +191,7 @@ impl GraphIr {
|
||||||
// no, not today
|
// no, not today
|
||||||
pub fn topological_sort(&self) -> Vec<Instruction> {
|
pub fn topological_sort(&self) -> Vec<Instruction> {
|
||||||
// count how many incoming edges each vertex has
|
// count how many incoming edges each vertex has
|
||||||
let input_counts: Map<_, usize> =
|
let nonzero_input_counts: Map<_, usize> =
|
||||||
self.rev_edges
|
self.rev_edges
|
||||||
.iter()
|
.iter()
|
||||||
.fold(Map::new(), |mut count, (input, _)| {
|
.fold(Map::new(), |mut count, (input, _)| {
|
||||||
|
@ -199,22 +199,14 @@ impl GraphIr {
|
||||||
count
|
count
|
||||||
});
|
});
|
||||||
|
|
||||||
// could experiment with a VecDeque here
|
// are there any unconnected ones we could start with?
|
||||||
let mut active_queue = Vec::new();
|
// TODO: experiment if a VecDeque with some ordering fun is digested better by the executor
|
||||||
|
let no_inputs: Vec<_> = {
|
||||||
// what vertices can we start with? in other words, which ones have 0 inputs?
|
let nonzero: Set<_> = nonzero_input_counts.keys().collect();
|
||||||
let unresolved_input_count: Map<id::Instruction, usize> = input_counts
|
let all: Set<_> = self.instructions.keys().collect();
|
||||||
.into_iter()
|
all.difference(&nonzero).copied().collect()
|
||||||
.filter_map(|(instr, count)| {
|
};
|
||||||
dbg!(count);
|
let mut active_queue = no_inputs;
|
||||||
if count == 0 {
|
|
||||||
active_queue.push(instr);
|
|
||||||
None
|
|
||||||
} else {
|
|
||||||
Some((instr, count))
|
|
||||||
}
|
|
||||||
})
|
|
||||||
.collect();
|
|
||||||
|
|
||||||
// then let's find the order!
|
// then let's find the order!
|
||||||
let mut order = Vec::new();
|
let mut order = Vec::new();
|
||||||
|
@ -224,25 +216,27 @@ impl GraphIr {
|
||||||
// make sure all dependents notice that
|
// make sure all dependents notice that
|
||||||
|
|
||||||
for dependent in self
|
for dependent in self
|
||||||
.dependents(¤t)
|
.dependents(current)
|
||||||
.expect("graph to be consistent")
|
.expect("graph to be consistent")
|
||||||
.flatten()
|
.flatten()
|
||||||
{
|
{
|
||||||
dbg!(dependent);
|
dbg!(dependent);
|
||||||
}
|
}
|
||||||
|
|
||||||
order.push(self.resolve(¤t).expect("graph to be consistent"));
|
// TODO: check if this instruction is "well-fed", that is, has all the inputs it needs,
|
||||||
|
// and if not, panic
|
||||||
|
order.push(self.resolve(current).expect("graph to be consistent"));
|
||||||
}
|
}
|
||||||
|
|
||||||
assert!(
|
assert!(
|
||||||
!unresolved_input_count.is_empty(),
|
!nonzero_input_counts.is_empty(),
|
||||||
concat!(
|
concat!(
|
||||||
"topological sort didn't cover all instructions\n",
|
"topological sort didn't cover all instructions\n",
|
||||||
"either there are unconnected inputs, or there is a cycle\n",
|
"either there are unconnected inputs, or there is a cycle\n",
|
||||||
"unresolved instructions:\n",
|
"unresolved instructions:\n",
|
||||||
"{:#?}"
|
"{:#?}"
|
||||||
),
|
),
|
||||||
unresolved_input_count
|
nonzero_input_counts,
|
||||||
);
|
);
|
||||||
|
|
||||||
order
|
order
|
||||||
|
|
Loading…
Reference in a new issue