Add second queue to make paralellization easier

This commit is contained in:
Daniel S. 2019-06-06 18:22:45 +02:00
parent 6365c58bd4
commit f00237cb65
1 changed files with 55 additions and 43 deletions

View File

@ -5,6 +5,8 @@ extern crate serde_derive;
extern crate fnv; extern crate fnv;
extern crate humantime; extern crate humantime;
// extern crate rayon;
// use rayon::prelude::*;
use fnv::{FnvHashMap, FnvHashSet}; use fnv::{FnvHashMap, FnvHashSet};
use humantime::format_duration; use humantime::format_duration;
use rstar::{PointDistance, RTree, RTreeObject, AABB}; use rstar::{PointDistance, RTree, RTreeObject, AABB};
@ -181,7 +183,7 @@ impl Router {
return self.scoopable.contains(&sys.id); return self.scoopable.contains(&sys.id);
} }
pub fn route(&mut self, src: &[f32; 3], dst: &[f32; 3]) -> Vec<(&System, &Point)> { pub fn route(&mut self, src: &[f32; 3], dst: &[f32; 3]) -> Option<Vec<(&System, &Point)>> {
let start_sys = self.closest(src); let start_sys = self.closest(src);
let goal_sys = self.closest(dst); let goal_sys = self.closest(dst);
let total = self.tree.size() as f32; let total = self.tree.size() as f32;
@ -189,57 +191,63 @@ impl Router {
let mut seen = FnvHashSet::default(); let mut seen = FnvHashSet::default();
let t_start = Instant::now(); let t_start = Instant::now();
let mut depth = 0; let mut depth = 0;
let mut found = false;
let mut queue: VecDeque<(usize, &Point)> = VecDeque::new(); let mut queue: VecDeque<(usize, &Point)> = VecDeque::new();
let mut r_queue: VecDeque<(usize, &Point)> = VecDeque::new(); let mut queue_next: VecDeque<(usize, &Point)> = VecDeque::new();
queue.push_front((0, &start_sys)); queue.push_front((0, &start_sys));
r_queue.push_front((0, &goal_sys));
seen.insert(start_sys.id); seen.insert(start_sys.id);
while let Some((d, sys)) = queue.pop_front() { while !queue.is_empty() {
if d != depth { while let Some((d, sys)) = queue.pop_front() {
depth = d; if d != depth {
print!( depth = d;
"\r[{}] Depth: {}, Queue: {}, Seen: {} ({:.2}%) ", print!(
format_duration(t_start.elapsed()), "\r[{}] Depth: {}, Queue: {}, Seen: {} ({:.2}%) ",
d, format_duration(t_start.elapsed()),
queue.len(), d,
prev.len(), queue.len(),
((prev.len() as f32) / total) * 100.0 prev.len(),
); ((prev.len() as f32) / total) * 100.0
std::io::stdout().flush().unwrap(); );
} std::io::stdout().flush().unwrap();
if sys.id == goal_sys.id { }
println!(); if sys.id == goal_sys.id {
let points = self.preload_points(); found = true;
let mut v: Vec<(&System, &Point)> = Vec::new(); break;
let mut prev_sys_id = sys.id; }
loop { let nbs = self
if let Some(sys) = self.systems.get(&prev_sys_id) { .neighbours(&sys)
v.push((sys, points[&sys.id])); .filter(|&nb| (self.valid(nb) || (nb.id == goal_sys.id)));
} else { for nb in nbs {
break; if seen.insert(nb.id) {
}; prev.insert(nb.id, sys.id);
match prev.get(&prev_sys_id) { queue_next.push_back((d + 1, nb));
Some(sys_id) => prev_sys_id = *sys_id,
None => {
break;
}
} }
} }
v.reverse();
return v;
} }
let nbs = self std::mem::swap(&mut queue, &mut queue_next);
.neighbours(&sys) }
.filter(|&nb| (self.valid(nb) || (nb.id == goal_sys.id))); println!();
for nb in nbs { if !found {
if seen.insert(nb.id) { return None;
prev.insert(nb.id, sys.id); }
queue.push_back((d + 1, nb)); let points = self.preload_points();
let mut v: Vec<(&System, &Point)> = Vec::new();
let mut prev_sys_id = goal_sys.id;
loop {
if let Some(sys) = self.systems.get(&prev_sys_id) {
v.push((sys, points[&sys.id]));
} else {
break;
};
match prev.get(&prev_sys_id) {
Some(sys_id) => prev_sys_id = *sys_id,
None => {
break;
} }
} }
} }
println!("No route found!"); v.reverse();
return Vec::new(); return Some(v);
} }
} }
@ -254,6 +262,10 @@ fn main() {
&[-1111.5625, -134.21875, 65269.75], // Beagle Point &[-1111.5625, -134.21875, 65269.75], // Beagle Point
// &[-7095.375, 401.25, 2396.8125], // V1357 Cygni, // &[-7095.375, 401.25, 2396.8125], // V1357 Cygni,
); // Ix -> BP 537 ); // Ix -> BP 537
let route = match route {
Some(r) => r,
None => Vec::new(),
};
println!( println!(
"Done in {} ({} Jumps)!\n", "Done in {} ({} Jumps)!\n",
format_duration(t_route.elapsed()), format_duration(t_route.elapsed()),