use std::time::Duration;
mod build_td;
pub(crate) mod engine;
pub(crate) mod execution;
mod graph;
mod greedy;
mod nested_dissection;
mod order;
mod preprocess;
mod vertex_cover_separator;
#[cfg(test)]
mod tests;
use execution::ElimStop;
pub use order::Order;
pub fn decompose(
graph: &crate::Graph,
order: Order<'_>,
seed: u64,
soft_budget: Option<Duration>,
) -> Result<crate::TreeDecomposition, crate::Error> {
if let Some(weights) = order.tie_weights()
&& weights.len() != graph.num_vertices as usize
{
return Err(crate::Error::InvalidInput(format!(
"sampled elimination has {} weights for {} vertices",
weights.len(),
graph.num_vertices
)));
}
let deadlines = crate::deadline::two_stage(crate::meter::now(), soft_budget, "elimination")?;
let mut prebuilt = engine::prebuild(graph);
let run = engine::run_order_prebuilt(
&mut prebuilt,
engine::RunSpec {
order,
seed,
stop: ElimStop {
soft_deadline: deadlines.soft,
hard_deadline: deadlines.hard,
width_bound: None,
},
complete_on_deadline: true,
},
);
match run {
engine::OrderRun::Completed(decomposition)
| engine::OrderRun::CompletedAtDeadline(decomposition) => Ok(decomposition),
engine::OrderRun::DeadlineAborted | engine::OrderRun::WidthAborted => {
unreachable!("a deadline-completing, unbounded run must produce a decomposition")
}
}
}