use crate::geometry::Geometry;
use geometry_tag::LinestringTag;
pub trait Linestring: Geometry<Kind = LinestringTag> {
fn points(&self) -> impl ExactSizeIterator<Item = &Self::Point> + Clone;
}
#[cfg(test)]
mod tests {
extern crate alloc;
use super::*;
use crate::point::Point;
use alloc::vec;
use alloc::vec::Vec;
use geometry_cs::Cartesian;
use geometry_tag::PointTag;
struct Xy(f64, f64);
impl Geometry for Xy {
type Kind = PointTag;
type Point = Self;
}
impl Point for Xy {
type Scalar = f64;
type Cs = Cartesian;
const DIM: usize = 2;
fn get<const D: usize>(&self) -> f64 {
if D == 0 { self.0 } else { self.1 }
}
}
struct VLs(Vec<Xy>);
impl Geometry for VLs {
type Kind = LinestringTag;
type Point = Xy;
}
impl Linestring for VLs {
fn points(&self) -> impl ExactSizeIterator<Item = &Xy> + Clone {
self.0.iter()
}
}
#[test]
fn linestring_iterates_in_declared_order() {
let ls = VLs(vec![Xy(0.0, 0.0), Xy(3.0, 4.0), Xy(4.0, 3.0)]);
assert_eq!(ls.points().count(), 3);
let xs: Vec<f64> = ls.points().map(Xy::get::<0>).collect();
assert_eq!(xs, vec![0.0, 3.0, 4.0]);
let ys: Vec<f64> = ls.points().map(Xy::get::<1>).collect();
assert_eq!(ys, vec![0.0, 4.0, 3.0]);
}
#[test]
fn linestring_iterator_reports_exact_size_and_clones() {
let ls = VLs(vec![Xy(0.0, 0.0), Xy(1.0, 1.0)]);
let it = ls.points();
assert_eq!(it.len(), 2);
let it2 = it.clone();
assert_eq!(it.count(), 2);
assert_eq!(it2.count(), 2);
}
}