Skip to main content

solverforge_solver/heuristic/move/
dynamic_list_change.rs

1use std::borrow::Cow;
2use std::fmt::Debug;
3
4use solverforge_core::domain::{DynamicListVariableSlot, PlanningSolution};
5use solverforge_scoring::Director;
6
7use super::list_kernel::{
8    change_candidate_trace_identity, change_do_move, change_is_doable, change_tabu_signature,
9    change_undo_move, ChangeCoordinates,
10};
11use super::{Move, MoveTabuSignature};
12
13pub struct DynamicListChangeMove<S> {
14    slot: DynamicListVariableSlot<S>,
15    source_entity_index: usize,
16    source_position: usize,
17    dest_entity_index: usize,
18    dest_position: usize,
19    indices: [usize; 2],
20}
21
22impl<S> Debug for DynamicListChangeMove<S> {
23    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
24        f.debug_struct("DynamicListChangeMove")
25            .field("source_entity", &self.source_entity_index)
26            .field("source_position", &self.source_position)
27            .field("dest_entity", &self.dest_entity_index)
28            .field("dest_position", &self.dest_position)
29            .field("variable_name", &self.slot.variable_name)
30            .finish()
31    }
32}
33
34impl<S> DynamicListChangeMove<S> {
35    pub fn new(
36        slot: DynamicListVariableSlot<S>,
37        source_entity_index: usize,
38        source_position: usize,
39        dest_entity_index: usize,
40        dest_position: usize,
41    ) -> Self {
42        Self {
43            slot,
44            source_entity_index,
45            source_position,
46            dest_entity_index,
47            dest_position,
48            indices: [source_entity_index, dest_entity_index],
49        }
50    }
51
52    fn is_intra_list(&self) -> bool {
53        self.source_entity_index == self.dest_entity_index
54    }
55
56    pub fn source_entity_index(&self) -> usize {
57        self.source_entity_index
58    }
59
60    pub fn source_position(&self) -> usize {
61        self.source_position
62    }
63
64    pub fn dest_entity_index(&self) -> usize {
65        self.dest_entity_index
66    }
67
68    pub fn dest_position(&self) -> usize {
69        self.dest_position
70    }
71
72    fn coordinates(&self) -> ChangeCoordinates {
73        ChangeCoordinates {
74            source_entity: self.source_entity_index,
75            source_position: self.source_position,
76            destination_entity: self.dest_entity_index,
77            destination_position: self.dest_position,
78        }
79    }
80}
81
82impl<S> Move<S> for DynamicListChangeMove<S>
83where
84    S: PlanningSolution,
85{
86    type Undo = ();
87
88    fn is_doable<D: Director<S>>(&self, score_director: &D) -> bool {
89        change_is_doable(&self.slot, self.coordinates(), score_director)
90    }
91
92    fn do_move<D: Director<S>>(&self, score_director: &mut D) -> Self::Undo {
93        change_do_move(&self.slot, self.coordinates(), score_director);
94    }
95
96    fn undo_move<D: Director<S>>(&self, score_director: &mut D, (): Self::Undo) {
97        change_undo_move(&self.slot, self.coordinates(), score_director);
98    }
99
100    fn descriptor_index(&self) -> usize {
101        self.slot.descriptor_index()
102    }
103
104    fn entity_indices(&self) -> &[usize] {
105        if self.is_intra_list() {
106            &self.indices[0..1]
107        } else {
108            &self.indices
109        }
110    }
111
112    fn variable_name(&self) -> &str {
113        self.slot.variable_name
114    }
115
116    fn telemetry_label(&self) -> &'static str {
117        "dynamic_list_change"
118    }
119
120    fn tabu_signature<D: Director<S>>(&self, score_director: &D) -> Cow<'_, MoveTabuSignature> {
121        Cow::Owned(change_tabu_signature(
122            &self.slot,
123            self.coordinates(),
124            score_director,
125        ))
126    }
127
128    fn candidate_trace_identity(&self) -> Option<crate::stats::CandidateTraceIdentity> {
129        Some(change_candidate_trace_identity(
130            &self.slot,
131            self.coordinates(),
132        ))
133    }
134}