diff --git a/src/function/accumulated.rs b/src/function/accumulated.rs index 5a269c7f..7d54a9f8 100644 --- a/src/function/accumulated.rs +++ b/src/function/accumulated.rs @@ -1,5 +1,3 @@ -use std::collections::VecDeque; - use crate::{accumulator, hash::FxHashSet, storage::DatabaseGen, DatabaseKeyIndex, Id}; use super::{Configuration, IngredientImpl}; @@ -24,19 +22,20 @@ where self.fetch(db, key); let db_key = self.database_key_index(key); - let mut visited: FxHashSet = std::iter::once(db_key).collect(); - let mut queue: VecDeque = std::iter::once(db_key).collect(); + let mut visited: FxHashSet = FxHashSet::default(); + let mut stack: Vec = vec![db_key]; - while let Some(k) = queue.pop_front() { + while let Some(k) = stack.pop() { + visited.insert(k); accumulator.produced_by(runtime, k, &mut output); let origin = db.lookup_ingredient(k.ingredient_index).origin(k.key_index); let inputs = origin.iter().flat_map(|origin| origin.inputs()); - for input in inputs { + for input in inputs.rev() { if let Ok(input) = input.try_into() { - if visited.insert(input) { - queue.push_back(input); + if !visited.contains(&input) { + stack.push(input); } } } diff --git a/src/runtime/local_state.rs b/src/runtime/local_state.rs index 2213bf1f..2619d85a 100644 --- a/src/runtime/local_state.rs +++ b/src/runtime/local_state.rs @@ -77,7 +77,7 @@ pub enum QueryOrigin { impl QueryOrigin { /// Indices for queries *read* by this query - pub(crate) fn inputs(&self) -> impl Iterator + '_ { + pub(crate) fn inputs(&self) -> impl DoubleEndedIterator + '_ { let opt_edges = match self { QueryOrigin::Derived(edges) | QueryOrigin::DerivedUntracked(edges) => Some(edges), QueryOrigin::Assigned(_) | QueryOrigin::BaseInput => None, @@ -86,7 +86,7 @@ impl QueryOrigin { } /// Indices for queries *written* by this query (if any) - pub(crate) fn outputs(&self) -> impl Iterator + '_ { + pub(crate) fn outputs(&self) -> impl DoubleEndedIterator + '_ { let opt_edges = match self { QueryOrigin::Derived(edges) | QueryOrigin::DerivedUntracked(edges) => Some(edges), QueryOrigin::Assigned(_) | QueryOrigin::BaseInput => None, @@ -127,7 +127,7 @@ impl QueryEdges { /// Returns the (tracked) inputs that were executed in computing this memoized value. /// /// These will always be in execution order. - pub(crate) fn inputs(&self) -> impl Iterator + '_ { + pub(crate) fn inputs(&self) -> impl DoubleEndedIterator + '_ { self.input_outputs .iter() .filter(|(edge_kind, _)| *edge_kind == EdgeKind::Input) @@ -137,7 +137,7 @@ impl QueryEdges { /// Returns the (tracked) outputs that were executed in computing this memoized value. /// /// These will always be in execution order. - pub(crate) fn outputs(&self) -> impl Iterator + '_ { + pub(crate) fn outputs(&self) -> impl DoubleEndedIterator + '_ { self.input_outputs .iter() .filter(|(edge_kind, _)| *edge_kind == EdgeKind::Output)