pumpkin_core/api/outputs/mod.rs
1use self::unsatisfiable::UnsatisfiableUnderAssumptions;
2pub use crate::basic_types::ProblemSolution;
3use crate::basic_types::Solution;
4pub use crate::basic_types::SolutionReference;
5use crate::Solver;
6pub mod solution_iterator;
7pub mod unsatisfiable;
8use crate::branching::Brancher;
9#[cfg(doc)]
10use crate::termination::TerminationCondition;
11
12/// The result of a call to [`Solver::satisfy`].
13#[derive(Debug)]
14pub enum SatisfactionResult<'solver, 'brancher, B: Brancher> {
15 /// Indicates that a solution was found.
16 ///
17 /// The solution can be obtained with [`Satisfiable::solution`], as well as the solver and
18 /// brancher. The solver and brancher may be of interest to e.g. log statistics. When the
19 /// result is dropped, the solver will be reset to the root, ready for further use.
20 Satisfiable(Satisfiable<'solver, 'brancher, B>),
21 /// Indicates that there is no solution to the satisfaction problem.
22 Unsatisfiable(&'solver Solver, &'brancher B),
23 /// Indicates that it is not known whether a solution exists. This is likely due to a
24 /// [`TerminationCondition`] triggering.
25 Unknown(&'solver Solver, &'brancher B),
26}
27
28/// The result of a call to [`Solver::satisfy_under_assumptions`].
29#[derive(Debug)]
30pub enum SatisfactionResultUnderAssumptions<'solver, 'brancher, B: Brancher> {
31 /// See documentation on [`SatisfactionResult::Satisfiable`].
32 Satisfiable(Satisfiable<'solver, 'brancher, B>),
33 /// Indicates that there is no solution to the satisfaction problem due to the provided
34 /// assumptions. It returns an [`UnsatisfiableUnderAssumptions`] which can be used to retrieve
35 /// an unsatisfiable core.
36 UnsatisfiableUnderAssumptions(UnsatisfiableUnderAssumptions<'solver, 'brancher, B>),
37 /// Indicates that there is no solution to the satisfaction problem.
38 Unsatisfiable(&'solver Solver),
39 /// Indicates that it is not known whether a solution exists. This is likely due to a
40 /// [`TerminationCondition`] triggering.
41 Unknown(&'solver Solver),
42}
43
44/// The result of a call to [`Solver::optimise`].
45#[derive(Debug)]
46pub enum OptimisationResult {
47 /// Indicates that an optimal solution has been found and proven to be optimal. It provides an
48 /// instance of [`Solution`] which contains the optimal solution.
49 Optimal(Solution),
50 /// Indicates that a solution was found and provides an instance of [`Solution`] which contains
51 /// best known solution by the solver.
52 Satisfiable(Solution),
53 /// Indicates that there is no solution to the problem.
54 Unsatisfiable,
55 /// Indicates that it is not known whether a solution exists. This is likely due to a
56 /// [`TerminationCondition`] triggering.
57 Unknown,
58}
59
60#[derive(Debug)]
61pub struct Satisfiable<'solver, 'brancher, B: Brancher> {
62 solver: &'solver mut Solver,
63 brancher: &'brancher mut B,
64}
65
66impl<'solver, 'brancher, B: Brancher> Satisfiable<'solver, 'brancher, B> {
67 pub(crate) fn new(solver: &'solver mut Solver, brancher: &'brancher mut B) -> Self {
68 Satisfiable { solver, brancher }
69 }
70
71 /// Get the solution that was discovered.
72 pub fn solution(&self) -> SolutionReference<'_> {
73 self.solver.get_solution_reference()
74 }
75
76 /// Get the solver instance.
77 pub fn solver(&self) -> &Solver {
78 self.solver
79 }
80
81 /// Get the brancher.
82 pub fn brancher(&self) -> &B {
83 self.brancher
84 }
85}
86
87impl<B: Brancher> Drop for Satisfiable<'_, '_, B> {
88 fn drop(&mut self) {
89 self.solver
90 .satisfaction_solver
91 .restore_state_at_root(self.brancher);
92 }
93}