Lots of improvements

This commit is contained in:
Andras Schmelczer 2026-02-22 21:09:07 +00:00
parent 205302dbb8
commit eb02b5832b
39 changed files with 699 additions and 271 deletions

View file

@ -22,18 +22,8 @@ pub struct PlaceData {
fn type_rank(place_type: &str) -> u8 {
match place_type {
"city" => 0,
"borough" => 1,
"town" => 2,
"suburb" => 3,
"quarter" => 4,
"neighbourhood" => 5,
"village" => 6,
"station" => 7,
"island" => 8,
"hamlet" => 9,
"locality" => 10,
"isolated_dwelling" => 11,
_ => 12,
"station" => 1,
_ => 2,
}
}
@ -159,10 +149,7 @@ mod tests {
#[test]
fn type_rank_ordering() {
assert!(type_rank("city") < type_rank("town"));
assert!(type_rank("town") < type_rank("suburb"));
assert!(type_rank("suburb") < type_rank("village"));
assert!(type_rank("village") < type_rank("hamlet"));
assert!(type_rank("hamlet") < type_rank("isolated_dwelling"));
assert!(type_rank("city") < type_rank("station"));
assert!(type_rank("station") < type_rank("unknown"));
}
}

View file

@ -8,8 +8,15 @@ use polars::lazy::frame::LazyFrame;
use rustc_hash::{FxHashMap, FxHashSet};
use tracing::info;
/// Cached postcode → travel_minutes mapping for a single destination file.
pub type TravelData = Arc<FxHashMap<String, i16>>;
/// Per-postcode travel time data: median and optional best-case (transit only).
#[derive(Clone, Copy)]
pub struct TravelDataRow {
pub minutes: i16,
pub best_minutes: Option<i16>,
}
/// Cached postcode → travel time data for a single destination file.
pub type TravelData = Arc<FxHashMap<String, TravelDataRow>>;
/// Simple LRU cache for travel time data, limited to `capacity` entries.
struct LruCache {
@ -159,12 +166,23 @@ impl TravelTimeStore {
.context("Missing 'travel_minutes' column")?
.i16()
.context("'travel_minutes' is not i16")?;
let best = df
.column("best_minutes")
.ok()
.map(|col| col.i16().expect("'best_minutes' is not i16"));
let mut map = FxHashMap::default();
map.reserve(df.height());
for (pc, min) in postcodes.into_iter().zip(minutes.into_iter()) {
for (i, (pc, min)) in postcodes.into_iter().zip(minutes.into_iter()).enumerate() {
if let (Some(pc), Some(min)) = (pc, min) {
map.insert(pc.to_string(), min);
let best_min = best.as_ref().and_then(|b| b.get(i));
map.insert(
pc.to_string(),
TravelDataRow {
minutes: min,
best_minutes: best_min,
},
);
}
}