Mon, 06 Jan 2025 20:29:25 -0500
More Serialize / Deserialize / Debug derives
0 | 1 | |
2 | use std::collections::BinaryHeap; | |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
3 | use std::cmp::{PartialOrd, Ord, Ordering, Ordering::*, max}; |
0 | 4 | use std::marker::PhantomData; |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
5 | use std::sync::{Arc, Mutex, MutexGuard, Condvar}; |
86
d5b0e496b72f
More Serialize / Deserialize / Debug derives
Tuomo Valkonen <tuomov@iki.fi>
parents:
55
diff
changeset
|
6 | use serde::{Serialize, Deserialize}; |
0 | 7 | use crate::types::*; |
5 | 8 | use crate::nanleast::NaNLeast; |
9 | use crate::sets::Cube; | |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
10 | use crate::parallelism::{thread_pool_size, thread_pool}; |
0 | 11 | use super::support::*; |
12 | use super::bt::*; | |
13 | use super::aggregator::*; | |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
14 | use crate::parallelism::TaskBudget; |
0 | 15 | |
16 | /// Trait for sorting [`Aggregator`]s for [`BT`] refinement. | |
17 | /// | |
5 | 18 | /// The sorting involves two sorting keys, the “upper” and the “lower” key. Any [`BT`] nodes |
0 | 19 | /// with upper key less the lower key of another are discarded from the refinement process. |
5 | 20 | /// Nodes with the highest upper sorting key are picked for refinement. |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
21 | pub trait AggregatorSorting : Sync + Send + 'static { |
0 | 22 | // Priority |
23 | type Agg : Aggregator; | |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
24 | type Sort : Ord + Copy + std::fmt::Debug + Sync + Send; |
0 | 25 | |
26 | /// Returns lower sorting key | |
27 | fn sort_lower(aggregator : &Self::Agg) -> Self::Sort; | |
28 | ||
29 | /// Returns upper sorting key | |
30 | fn sort_upper(aggregator : &Self::Agg) -> Self::Sort; | |
31 | ||
5 | 32 | /// Returns a sorting key that is less than any other sorting key. |
0 | 33 | fn bottom() -> Self::Sort; |
34 | } | |
35 | ||
36 | /// An [`AggregatorSorting`] for [`Bounds`], using the upper/lower bound as the upper/lower key. | |
37 | /// | |
38 | /// See [`LowerBoundSorting`] for the opposite ordering. | |
86
d5b0e496b72f
More Serialize / Deserialize / Debug derives
Tuomo Valkonen <tuomov@iki.fi>
parents:
55
diff
changeset
|
39 | #[derive(Debug, Clone, Serialize, Deserialize)] |
d5b0e496b72f
More Serialize / Deserialize / Debug derives
Tuomo Valkonen <tuomov@iki.fi>
parents:
55
diff
changeset
|
40 | pub struct UpperBoundSorting<F : Float>( |
d5b0e496b72f
More Serialize / Deserialize / Debug derives
Tuomo Valkonen <tuomov@iki.fi>
parents:
55
diff
changeset
|
41 | #[serde(skip)] |
d5b0e496b72f
More Serialize / Deserialize / Debug derives
Tuomo Valkonen <tuomov@iki.fi>
parents:
55
diff
changeset
|
42 | PhantomData<F> |
d5b0e496b72f
More Serialize / Deserialize / Debug derives
Tuomo Valkonen <tuomov@iki.fi>
parents:
55
diff
changeset
|
43 | ); |
0 | 44 | |
45 | /// An [`AggregatorSorting`] for [`Bounds`], using the upper/lower bound as the lower/upper key. | |
46 | /// | |
47 | /// See [`UpperBoundSorting`] for the opposite ordering. | |
86
d5b0e496b72f
More Serialize / Deserialize / Debug derives
Tuomo Valkonen <tuomov@iki.fi>
parents:
55
diff
changeset
|
48 | #[derive(Debug, Clone, Serialize, Deserialize)] |
d5b0e496b72f
More Serialize / Deserialize / Debug derives
Tuomo Valkonen <tuomov@iki.fi>
parents:
55
diff
changeset
|
49 | pub struct LowerBoundSorting<F : Float>( |
d5b0e496b72f
More Serialize / Deserialize / Debug derives
Tuomo Valkonen <tuomov@iki.fi>
parents:
55
diff
changeset
|
50 | #[serde(skip)] |
d5b0e496b72f
More Serialize / Deserialize / Debug derives
Tuomo Valkonen <tuomov@iki.fi>
parents:
55
diff
changeset
|
51 | PhantomData<F> |
d5b0e496b72f
More Serialize / Deserialize / Debug derives
Tuomo Valkonen <tuomov@iki.fi>
parents:
55
diff
changeset
|
52 | ); |
0 | 53 | |
54 | impl<F : Float> AggregatorSorting for UpperBoundSorting<F> { | |
55 | type Agg = Bounds<F>; | |
56 | type Sort = NaNLeast<F>; | |
57 | ||
58 | #[inline] | |
59 | fn sort_lower(aggregator : &Bounds<F>) -> Self::Sort { NaNLeast(aggregator.lower()) } | |
60 | ||
61 | #[inline] | |
62 | fn sort_upper(aggregator : &Bounds<F>) -> Self::Sort { NaNLeast(aggregator.upper()) } | |
63 | ||
64 | #[inline] | |
65 | fn bottom() -> Self::Sort { NaNLeast(F::NEG_INFINITY) } | |
66 | } | |
67 | ||
68 | ||
69 | impl<F : Float> AggregatorSorting for LowerBoundSorting<F> { | |
70 | type Agg = Bounds<F>; | |
71 | type Sort = NaNLeast<F>; | |
72 | ||
73 | #[inline] | |
74 | fn sort_upper(aggregator : &Bounds<F>) -> Self::Sort { NaNLeast(-aggregator.lower()) } | |
75 | ||
76 | #[inline] | |
77 | fn sort_lower(aggregator : &Bounds<F>) -> Self::Sort { NaNLeast(-aggregator.upper()) } | |
78 | ||
79 | #[inline] | |
80 | fn bottom() -> Self::Sort { NaNLeast(F::NEG_INFINITY) } | |
81 | } | |
82 | ||
5 | 83 | /// Return type of [`Refiner::refine`]. |
84 | /// | |
85 | /// The parameter `R` is the result type of the refiner acting on an [`Aggregator`] of type `A`. | |
0 | 86 | pub enum RefinerResult<A : Aggregator, R> { |
5 | 87 | /// Indicates an insufficiently refined state: the [`BT`] needs to be further refined. |
0 | 88 | NeedRefinement, |
89 | /// Indicates a certain result `R`, stop refinement immediately. | |
90 | Certain(R), | |
91 | /// Indicates an uncertain result: continue refinement until candidates have been exhausted | |
92 | /// or a certain result found. | |
93 | Uncertain(A, R) | |
94 | } | |
95 | ||
96 | use RefinerResult::*; | |
97 | ||
5 | 98 | /// A `Refiner` is used to search a [`BT`], refining the subdivision when necessary. |
99 | /// | |
100 | /// The search is performed by [`BTSearch::search_and_refine`]. | |
101 | /// The `Refiner` is used to determine whether an [`Aggregator`] `A` stored in the [`BT`] is | |
102 | /// sufficiently refined within a [`Cube`], and in such a case, produce a desired result (e.g. | |
103 | /// a maximum value of a function). | |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
104 | pub trait Refiner<F : Float, A, G, const N : usize> : Sync + Send + 'static |
0 | 105 | where F : Num, |
106 | A : Aggregator, | |
107 | G : SupportGenerator<F, N> { | |
108 | ||
5 | 109 | /// The result type of the refiner |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
110 | type Result : std::fmt::Debug + Sync + Send + 'static; |
5 | 111 | /// The sorting to be employed by [`BTSearch::search_and_refine`] on node aggregators |
112 | /// to detemrine node priority. | |
0 | 113 | type Sorting : AggregatorSorting<Agg = A>; |
114 | ||
5 | 115 | /// Determines whether `aggregator` is sufficiently refined within `domain`. |
116 | /// | |
117 | /// If the aggregator is sufficiently refined that the desired `Self::Result` can be produced, | |
118 | /// a [`RefinerResult`]`::Certain` or `Uncertain` should be returned, depending on | |
119 | /// the confidence of the solution. In the uncertain case an improved aggregator should also | |
120 | /// be included. If the result cannot be produced, `NeedRefinement` should be | |
121 | /// returned. | |
122 | /// | |
123 | /// For example, if the refiner is used to minimise a function presented by the `BT`, | |
124 | /// an `Uncertain` result can be used to return a local maximum of the function on `domain` | |
125 | /// The result can be claimed `Certain` if it is a global maximum. In that case the | |
126 | /// refinment will stop immediately. A `NeedRefinement` result indicates that the `aggregator` | |
127 | /// and/or `domain` are not sufficiently refined to compute a lcoal maximum of sufficient | |
128 | /// quality. | |
129 | /// | |
130 | /// The vector `data` stored all the data of the [`BT`] in the node corresponding to `domain`. | |
131 | /// The `generator` can be used to convert `data` into [`Support`]s. The parameter `step` | |
132 | /// counts the calls to `refine`, and can be used to stop the refinement when a maximum | |
133 | /// number of steps is reached. | |
0 | 134 | fn refine( |
135 | &self, | |
136 | aggregator : &A, | |
137 | domain : &Cube<F, N>, | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
138 | data : &[G::Id], |
0 | 139 | generator : &G, |
140 | step : usize, | |
141 | ) -> RefinerResult<A, Self::Result>; | |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
142 | |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
143 | /// Fuse two [`Self::Result`]s (needed in threaded refinement). |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
144 | fn fuse_results(r1 : &mut Self::Result, r2 : Self::Result); |
0 | 145 | } |
146 | ||
147 | /// Structure for tracking the refinement process in a [`BinaryHeap`]. | |
86
d5b0e496b72f
More Serialize / Deserialize / Debug derives
Tuomo Valkonen <tuomov@iki.fi>
parents:
55
diff
changeset
|
148 | #[derive(Debug)] |
0 | 149 | struct RefinementInfo<'a, F, D, A, S, RResult, const N : usize, const P : usize> |
150 | where F : Float, | |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
151 | D : 'static, |
0 | 152 | A : Aggregator, |
153 | S : AggregatorSorting<Agg = A> { | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
154 | /// Domain of `node` |
0 | 155 | cube : Cube<F, N>, |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
156 | /// Node to be refined |
0 | 157 | node : &'a mut Node<F, D, A, N, P>, |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
158 | /// Result and improve aggregator for the [`Refiner`] |
0 | 159 | refiner_info : Option<(A, RResult)>, |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
160 | /// For [`AggregatorSorting`] being used for the type system |
0 | 161 | sorting : PhantomData<S>, |
162 | } | |
163 | ||
164 | impl<'a, F, D, A, S, RResult, const N : usize, const P : usize> | |
165 | RefinementInfo<'a, F, D, A, S, RResult, N, P> | |
166 | where F : Float, | |
167 | D : 'static, | |
168 | A : Aggregator, | |
169 | S : AggregatorSorting<Agg = A> { | |
170 | ||
171 | #[inline] | |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
172 | fn with_aggregator<U>(&self, f : impl FnOnce(&A) -> U) -> U { |
0 | 173 | match self.refiner_info { |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
174 | Some((ref agg, _)) => f(agg), |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
175 | None => f(&self.node.aggregator), |
0 | 176 | } |
177 | } | |
178 | ||
179 | #[inline] | |
180 | fn sort_lower(&self) -> S::Sort { | |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
181 | self.with_aggregator(S::sort_lower) |
0 | 182 | } |
183 | ||
184 | #[inline] | |
185 | fn sort_upper(&self) -> S::Sort { | |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
186 | self.with_aggregator(S::sort_upper) |
0 | 187 | } |
188 | } | |
189 | ||
190 | impl<'a, F, D, A, S, RResult, const N : usize, const P : usize> PartialEq | |
191 | for RefinementInfo<'a, F, D, A, S, RResult, N, P> | |
192 | where F : Float, | |
193 | D : 'static, | |
194 | A : Aggregator, | |
195 | S : AggregatorSorting<Agg = A> { | |
196 | ||
197 | #[inline] | |
198 | fn eq(&self, other : &Self) -> bool { self.cmp(other) == Equal } | |
199 | } | |
200 | ||
201 | impl<'a, F, D, A, S, RResult, const N : usize, const P : usize> PartialOrd | |
202 | for RefinementInfo<'a, F, D, A, S, RResult, N, P> | |
203 | where F : Float, | |
204 | D : 'static, | |
205 | A : Aggregator, | |
206 | S : AggregatorSorting<Agg = A> { | |
207 | ||
208 | #[inline] | |
209 | fn partial_cmp(&self, other : &Self) -> Option<Ordering> { Some(self.cmp(other)) } | |
210 | } | |
211 | ||
212 | impl<'a, F, D, A, S, RResult, const N : usize, const P : usize> Eq | |
213 | for RefinementInfo<'a, F, D, A, S, RResult, N, P> | |
214 | where F : Float, | |
215 | D : 'static, | |
216 | A : Aggregator, | |
217 | S : AggregatorSorting<Agg = A> { | |
218 | } | |
219 | ||
220 | impl<'a, F, D, A, S, RResult, const N : usize, const P : usize> Ord | |
221 | for RefinementInfo<'a, F, D, A, S, RResult, N, P> | |
222 | where F : Float, | |
223 | D : 'static, | |
224 | A : Aggregator, | |
225 | S : AggregatorSorting<Agg = A> { | |
226 | ||
227 | #[inline] | |
228 | fn cmp(&self, other : &Self) -> Ordering { | |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
229 | self.with_aggregator(|agg1| other.with_aggregator(|agg2| { |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
230 | match S::sort_upper(agg1).cmp(&S::sort_upper(agg2)) { |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
231 | Equal => S::sort_lower(agg1).cmp(&S::sort_lower(agg2)), |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
232 | order => order, |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
233 | } |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
234 | })) |
0 | 235 | } |
236 | } | |
237 | ||
5 | 238 | /// This is a container for a [`BinaryHeap`] of [`RefinementInfo`]s together with tracking of |
239 | /// the greatest lower bound of the [`Aggregator`]s of the [`Node`]s therein accroding to | |
240 | /// chosen [`AggregatorSorting`]. | |
86
d5b0e496b72f
More Serialize / Deserialize / Debug derives
Tuomo Valkonen <tuomov@iki.fi>
parents:
55
diff
changeset
|
241 | #[derive(Debug)] |
5 | 242 | struct HeapContainer<'a, F, D, A, S, RResult, const N : usize, const P : usize> |
0 | 243 | where F : Float, |
244 | D : 'static + Copy, | |
245 | Const<P> : BranchCount<N>, | |
246 | A : Aggregator, | |
247 | S : AggregatorSorting<Agg = A> { | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
248 | /// Priority queue of nodes to be refined |
0 | 249 | heap : BinaryHeap<RefinementInfo<'a, F, D, A, S, RResult, N, P>>, |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
250 | /// Maximum of node sorting lower bounds seen in the heap |
0 | 251 | glb : S::Sort, |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
252 | /// Number of insertions in the heap since previous prune |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
253 | insert_counter : usize, |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
254 | /// If a result has been found by some refinment threat, it is stored here |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
255 | result : Option<RResult>, |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
256 | /// Refinement step counter |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
257 | step : usize, |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
258 | /// Number of threads currently processing (not sleeping) |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
259 | n_processing : usize, |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
260 | /// Threshold for heap pruning |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
261 | heap_prune_threshold : usize, |
0 | 262 | } |
263 | ||
264 | impl<'a, F, D, A, S, RResult, const N : usize, const P : usize> | |
265 | HeapContainer<'a, F, D, A, S, RResult, N, P> | |
266 | where F : Float, | |
267 | D : 'static + Copy, | |
268 | Const<P> : BranchCount<N>, | |
269 | A : Aggregator, | |
270 | S : AggregatorSorting<Agg = A> { | |
271 | ||
5 | 272 | /// Push `ri` into the [`BinaryHeap`]. Do greatest lower bound maintenance. |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
273 | /// |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
274 | /// Returns a boolean indicating whether the push was actually performed due to glb |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
275 | /// filtering or not. |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
276 | #[inline] |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
277 | fn push(&mut self, ri : RefinementInfo<'a, F, D, A, S, RResult, N, P>) -> bool { |
0 | 278 | if ri.sort_upper() >= self.glb { |
279 | let l = ri.sort_lower(); | |
280 | self.heap.push(ri); | |
281 | self.glb = self.glb.max(l); | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
282 | self.insert_counter += 1; |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
283 | true |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
284 | } else { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
285 | false |
0 | 286 | } |
287 | } | |
288 | } | |
289 | ||
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
290 | impl<F : Float, D, A, const N : usize, const P : usize> |
0 | 291 | Branches<F,D,A,N,P> |
292 | where Const<P> : BranchCount<N>, | |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
293 | A : Aggregator, |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
294 | D : 'static + Copy + Send + Sync { |
0 | 295 | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
296 | /// Stage all subnodes of `self` into the refinement queue `container`. |
0 | 297 | fn stage_refine<'a, S, RResult>( |
298 | &'a mut self, | |
299 | domain : Cube<F,N>, | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
300 | container : &mut HeapContainer<'a, F, D, A, S, RResult, N, P>, |
0 | 301 | ) where S : AggregatorSorting<Agg = A> { |
302 | // Insert all subnodes into the refinement heap. | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
303 | for (node, cube) in self.nodes_and_cubes_mut(&domain) { |
0 | 304 | container.push(RefinementInfo { |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
305 | cube, |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
306 | node, |
0 | 307 | refiner_info : None, |
308 | sorting : PhantomData, | |
309 | }); | |
310 | } | |
311 | } | |
312 | } | |
313 | ||
314 | ||
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
315 | impl<F : Float, D, A, const N : usize, const P : usize> |
0 | 316 | Node<F,D,A,N,P> |
317 | where Const<P> : BranchCount<N>, | |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
318 | A : Aggregator, |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
319 | D : 'static + Copy + Send + Sync { |
0 | 320 | |
321 | /// If `self` is a leaf node, uses the `refiner` to determine whether further subdivision | |
322 | /// is required to get a sufficiently refined solution for the problem the refiner is used | |
323 | /// to solve. If the refiner returns [`RefinerResult::Certain`] result, it is returned. | |
324 | /// If [`RefinerResult::Uncertain`] is returned, the leaf is inserted back into the refinement | |
325 | /// queue `container`. If `self` is a branch, its subnodes are staged into `container` using | |
326 | /// [`Branches::stage_refine`]. | |
5 | 327 | /// |
328 | /// `domain`, as usual, indicates the spatial area corresponding to `self`. | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
329 | fn search_and_refine<'a, 'b, 'c, R, G>( |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
330 | self : &'a mut Self, |
0 | 331 | domain : Cube<F,N>, |
332 | refiner : &R, | |
333 | generator : &G, | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
334 | container_arc : &'c Arc<Mutex<HeapContainer<'a, F, D, A, R::Sorting, R::Result, N, P>>>, |
0 | 335 | step : usize |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
336 | ) -> Result<R::Result, MutexGuard<'c, HeapContainer<'a, F, D, A, R::Sorting, R::Result, N, P>>> |
0 | 337 | where R : Refiner<F, A, G, N>, |
338 | G : SupportGenerator<F, N, Id=D>, | |
339 | G::SupportType : LocalAnalysis<F, A, N> { | |
340 | ||
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
341 | //drop(container); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
342 | |
0 | 343 | // Refine a leaf. |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
344 | let res = match self.data { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
345 | NodeOption::Leaf(ref mut v) => { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
346 | let res = refiner.refine(&self.aggregator, &domain, v, generator, step); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
347 | if let NeedRefinement = res { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
348 | // The refiner has deemed the leaf unsufficiently refined, so subdivide |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
349 | // it and add the new nodes into the refinement priority heap. |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
350 | let mut it = v.iter(); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
351 | // Only create new branches if there's anything to add. |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
352 | // We insert the last item first to mix the support_hint a bit. |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
353 | if let Some(&d0) = it.next_back() { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
354 | // Construct new Branches |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
355 | let support = generator.support_for(d0); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
356 | let mut b = Branches::new_with(&domain, &support); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
357 | b.insert(&domain, d0, Const::<1>, &support, TaskBudget::none()); |
0 | 358 | for &d in it { |
359 | let support = generator.support_for(d); | |
360 | // TODO: can we be smarter than just refining one level? | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
361 | b.insert(&domain, d, Const::<1>, &support, TaskBudget::none()); |
0 | 362 | } |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
363 | // Update current node and stage refinement of new branches. |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
364 | b.summarise_into(&mut self.aggregator); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
365 | // FIXME: parent aggregators are not updated and will be out-of-date, but |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
366 | // right now pointsource_algs is not really taking advantage of the |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
367 | // aggregators being updated. Moreover, insertion and aggregator refinement |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
368 | // code in `bt.rs` will overflow the stack in deeply nested trees. |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
369 | // We nevertheless need to store `b` into `self` to be able to queue |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
370 | // the branches. |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
371 | self.data = NodeOption::Branches(Arc::new(b)); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
372 | // This ugly match is needed to keep the compiler happy about lifetimes. |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
373 | match self.data { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
374 | NodeOption::Branches(ref mut arc_b) => { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
375 | let mut container = container_arc.lock().unwrap(); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
376 | // Safe: we just created arg_b and have a mutable exclusive |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
377 | // reference to self containing it. |
55
7b2ee3e84c5f
Add "nightly" feature and provide alternative low-performance implementations of several things when not available.
Tuomo Valkonen <tuomov@iki.fi>
parents:
9
diff
changeset
|
378 | #[cfg(feature = "nightly")] |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
379 | unsafe { Arc::get_mut_unchecked(arc_b) } |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
380 | .stage_refine(domain, &mut *container); |
55
7b2ee3e84c5f
Add "nightly" feature and provide alternative low-performance implementations of several things when not available.
Tuomo Valkonen <tuomov@iki.fi>
parents:
9
diff
changeset
|
381 | #[cfg(not(feature = "nightly"))] |
7b2ee3e84c5f
Add "nightly" feature and provide alternative low-performance implementations of several things when not available.
Tuomo Valkonen <tuomov@iki.fi>
parents:
9
diff
changeset
|
382 | Arc::get_mut(arc_b).unwrap() |
7b2ee3e84c5f
Add "nightly" feature and provide alternative low-performance implementations of several things when not available.
Tuomo Valkonen <tuomov@iki.fi>
parents:
9
diff
changeset
|
383 | .stage_refine(domain, &mut *container); |
7b2ee3e84c5f
Add "nightly" feature and provide alternative low-performance implementations of several things when not available.
Tuomo Valkonen <tuomov@iki.fi>
parents:
9
diff
changeset
|
384 | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
385 | return Err(container) |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
386 | }, |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
387 | _ => unreachable!("This cannot happen"), |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
388 | } |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
389 | } |
0 | 390 | } |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
391 | res |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
392 | }, |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
393 | NodeOption::Branches(ref mut b) => { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
394 | // Insert branches into refinement priority queue. |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
395 | let mut container = container_arc.lock().unwrap(); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
396 | Arc::make_mut(b).stage_refine(domain, &mut *container); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
397 | return Err(container) |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
398 | }, |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
399 | NodeOption::Uninitialised => { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
400 | refiner.refine(&self.aggregator, &domain, &[], generator, step) |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
401 | }, |
0 | 402 | }; |
403 | ||
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
404 | match res { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
405 | Uncertain(agg, val) => { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
406 | // The refiner gave an undertain result. Push a leaf back into the refinement queue |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
407 | // with the new refined aggregator and custom return value. It will be popped and |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
408 | // returned in the loop of [`BTSearch::search_and_refine`] when there are no |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
409 | // unrefined candidates that could potentially be better according to their basic |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
410 | // aggregator. |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
411 | let mut container = container_arc.lock().unwrap(); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
412 | container.push(RefinementInfo { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
413 | cube : domain, |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
414 | node : self, |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
415 | refiner_info : Some((agg, val)), |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
416 | sorting : PhantomData, |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
417 | }); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
418 | Err(container) |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
419 | }, |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
420 | Certain(val) => { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
421 | // The refiner gave a certain result so return it to allow early termination |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
422 | Ok(val) |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
423 | }, |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
424 | NeedRefinement => { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
425 | // This should only happen when we run into NodeOption::Uninitialised above. |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
426 | // There's really nothing to do. |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
427 | panic!("Do not know whow to refine uninitialised nodes"); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
428 | } |
0 | 429 | } |
430 | } | |
431 | } | |
432 | ||
5 | 433 | /// Interface trait to a refining search on a [`BT`]. |
434 | /// | |
435 | /// This can be removed and the methods implemented directly on [`BT`] once Rust's const generics | |
436 | /// are flexible enough to allow fixing `P=pow(2, N)`. | |
0 | 437 | pub trait BTSearch<F, const N : usize> : BTImpl<F, N> |
438 | where F : Float { | |
439 | ||
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
440 | /// Perform a search on on `Self`, as determined by `refiner`. |
5 | 441 | /// |
442 | /// Nodes are inserted in a priority queue and processed in the order determined by the | |
443 | /// [`AggregatorSorting`] [`Refiner::Sorting`]. Leaf nodes are subdivided until the refiner | |
444 | /// decides that a sufficiently refined leaf node has been found, as determined by either the | |
445 | /// refiner returning a [`RefinerResult::Certain`] result, or a previous | |
446 | /// [`RefinerResult::Uncertain`] result is found again at the top of the priority queue. | |
447 | /// | |
448 | /// The `generator` converts [`BTImpl::Data`] stored in the bisection tree into a [`Support`]. | |
0 | 449 | fn search_and_refine<'b, R, G>( |
450 | &'b mut self, | |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
451 | refiner : R, |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
452 | generator : &Arc<G>, |
0 | 453 | ) -> Option<R::Result> |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
454 | where R : Refiner<F, Self::Agg, G, N> + Sync + Send + 'static, |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
455 | G : SupportGenerator<F, N, Id=Self::Data> + Sync + Send + 'static, |
0 | 456 | G::SupportType : LocalAnalysis<F, Self::Agg, N>; |
457 | } | |
458 | ||
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
459 | fn refinement_loop<F : Float, D, A, R, G, const N : usize, const P : usize> ( |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
460 | wakeup : Option<Arc<Condvar>>, |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
461 | refiner : &R, |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
462 | generator_arc : &Arc<G>, |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
463 | container_arc : &Arc<Mutex<HeapContainer<F, D, A, R::Sorting, R::Result, N, P>>>, |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
464 | ) where A : Aggregator, |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
465 | R : Refiner<F, A, G, N>, |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
466 | G : SupportGenerator<F, N, Id=D>, |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
467 | G::SupportType : LocalAnalysis<F, A, N>, |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
468 | Const<P> : BranchCount<N>, |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
469 | D : 'static + Copy + Sync + Send + std::fmt::Debug { |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
470 | |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
471 | let mut did_park = true; |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
472 | let mut container = container_arc.lock().unwrap(); |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
473 | |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
474 | 'main: loop { |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
475 | // Find a node to process |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
476 | let ri = 'get_next: loop { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
477 | if did_park { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
478 | container.n_processing += 1; |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
479 | did_park = false; |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
480 | } |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
481 | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
482 | // Some refinement task/thread has found a result, return |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
483 | if container.result.is_some() { |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
484 | container.n_processing -= 1; |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
485 | break 'main |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
486 | } |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
487 | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
488 | match container.heap.pop() { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
489 | // There's work to be done. |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
490 | Some(ri) => break 'get_next ri, |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
491 | // No work to be done; park if some task/thread is still processing nodes, |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
492 | // fail if not. |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
493 | None => { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
494 | debug_assert!(container.n_processing > 0); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
495 | container.n_processing -= 1; |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
496 | if container.n_processing == 0 { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
497 | break 'main; |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
498 | } else if let Some(ref c) = wakeup { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
499 | did_park = true; |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
500 | container = c.wait(container).unwrap(); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
501 | continue 'get_next; |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
502 | } else { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
503 | break 'main |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
504 | } |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
505 | } |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
506 | }; |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
507 | }; |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
508 | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
509 | let step = container.step; |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
510 | container.step += 1; |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
511 | |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
512 | if let Some((_, result)) = ri.refiner_info { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
513 | // Terminate based on a “best possible” result. |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
514 | container.result = Some(result); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
515 | container.n_processing -= 1; |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
516 | break 'main |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
517 | } |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
518 | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
519 | // Do priority queue maintenance |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
520 | if container.insert_counter > container.heap_prune_threshold { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
521 | // Make sure glb is good. |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
522 | match container.heap.iter().map(|ri| ri.sort_lower()).reduce(max) { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
523 | Some(glb) => { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
524 | container.glb = glb; |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
525 | // Prune |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
526 | container.heap.retain(|ri| ri.sort_upper() >= glb); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
527 | }, |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
528 | None => { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
529 | container.glb = R::Sorting::bottom() |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
530 | } |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
531 | } |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
532 | container.insert_counter = 0; |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
533 | } |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
534 | |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
535 | // Unlock the mutex… |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
536 | drop(container); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
537 | |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
538 | // … and process the node. We may get returned an already unlocked mutex. |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
539 | match Node::search_and_refine(ri.node, ri.cube, refiner, &**generator_arc, |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
540 | &container_arc, step) { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
541 | Ok(r) => { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
542 | let mut container = container_arc.lock().unwrap(); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
543 | // Terminate based on a certain result from the refiner |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
544 | match container.result { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
545 | Some(ref mut r_prev) => R::fuse_results(r_prev, r), |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
546 | None => container.result = Some(r), |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
547 | } |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
548 | break 'main |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
549 | }, |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
550 | Err(cnt) => { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
551 | container = cnt; |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
552 | // Wake up another thread if one is sleeping; there should be now work in the |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
553 | // queue. |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
554 | if let Some(ref c) = wakeup { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
555 | c.notify_one(); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
556 | } |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
557 | } |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
558 | } |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
559 | |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
560 | } |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
561 | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
562 | // Make sure no task is sleeping |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
563 | if let Some(ref c) = wakeup { |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
564 | c.notify_all(); |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
565 | } |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
566 | } |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
567 | |
0 | 568 | // Needed to get access to a Node without a trait interface. |
569 | macro_rules! impl_btsearch { | |
570 | ($($n:literal)*) => { $( | |
571 | impl<'a, M, F, D, A> | |
572 | BTSearch<F, $n> | |
573 | for BT<M,F,D,A,$n> | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
574 | where //Self : BTImpl<F,$n,Data=D,Agg=A, Depth=M>, // <== automatically deduced |
0 | 575 | M : Depth, |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
576 | F : Float + Send, |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
577 | A : Aggregator, |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
578 | D : 'static + Copy + Sync + Send + std::fmt::Debug { |
0 | 579 | fn search_and_refine<'b, R, G>( |
580 | &'b mut self, | |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
581 | refiner : R, |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
582 | generator : &Arc<G>, |
0 | 583 | ) -> Option<R::Result> |
584 | where R : Refiner<F, A, G, $n>, | |
585 | G : SupportGenerator<F, $n, Id=D>, | |
586 | G::SupportType : LocalAnalysis<F, A, $n> { | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
587 | let mut init_container = HeapContainer { |
0 | 588 | heap : BinaryHeap::new(), |
589 | glb : R::Sorting::bottom(), | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
590 | insert_counter : 0, |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
591 | result : None, |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
592 | step : 0, |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
593 | n_processing : 0, |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
594 | // An arbitrary threshold for starting pruning of the heap |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
595 | heap_prune_threshold : 2u32.pow(16.max($n * self.depth.value())) as usize |
0 | 596 | }; |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
597 | init_container.push(RefinementInfo { |
0 | 598 | cube : self.domain, |
599 | node : &mut self.topnode, | |
600 | refiner_info : None, | |
601 | sorting : PhantomData, | |
602 | }); | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
603 | |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
604 | let container_arc = Arc::new(Mutex::new(init_container)); |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
605 | if let Some(pool) = thread_pool() { |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
606 | let n = thread_pool_size(); |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
607 | pool.scope(|s| { |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
608 | let wakeup = Arc::new(Condvar::new()); |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
609 | for _ in 0..n { |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
610 | let refiner_ref = &refiner; |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
611 | let container_t = Arc::clone(&container_arc); |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
612 | let wakeup_t = Arc::clone(&wakeup); |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
613 | s.spawn(move |_| { |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
614 | refinement_loop(Some(wakeup_t), refiner_ref, generator, |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
615 | &container_t); |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
616 | }); |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
617 | } |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
618 | refinement_loop(Some(wakeup), &refiner, generator, &container_arc); |
8
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
619 | }); |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
620 | } else { |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
621 | refinement_loop(None, &refiner, generator, &container_arc); |
4e09b7829b51
Multithreaded bisection tree operations
Tuomo Valkonen <tuomov@iki.fi>
parents:
5
diff
changeset
|
622 | } |
0 | 623 | |
9
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
624 | match Arc::try_unwrap(container_arc) { |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
625 | Ok(mtx) => mtx.into_inner().unwrap().result, |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
626 | Err(_) => panic!("Refinement threads not finished properly."), |
f40dfaf2166d
Improvements and minor fixes to bisection tree refinement.
Tuomo Valkonen <tuomov@iki.fi>
parents:
8
diff
changeset
|
627 | } |
0 | 628 | } |
629 | } | |
630 | )* } | |
631 | } | |
632 | ||
633 | impl_btsearch!(1 2 3 4); | |
634 |