Skip to main content

shapefile/
geo_traits_impl.rs

1use std::hint::unreachable_unchecked;
2
3use crate::{
4    Multipoint, MultipointM, MultipointZ, Point, PointM, PointZ, PolygonRing, Polyline, PolylineM,
5    PolylineZ, NO_DATA,
6};
7use geo_traits::{
8    CoordTrait, GeometryTrait, LineStringTrait, MultiLineStringTrait, MultiPointTrait,
9    MultiPolygonTrait, PointTrait, PolygonTrait, UnimplementedLineString,
10    UnimplementedMultiLineString, UnimplementedMultiPoint, UnimplementedMultiPolygon,
11    UnimplementedPoint, UnimplementedPolygon,
12};
13
14// Shapefile points can't be null, so we implement both traits on them
15impl CoordTrait for Point {
16    type T = f64;
17
18    fn dim(&self) -> geo_traits::Dimensions {
19        geo_traits::Dimensions::Xy
20    }
21
22    fn nth_or_panic(&self, n: usize) -> Self::T {
23        match n {
24            0 => self.x(),
25            1 => self.y(),
26            _ => panic!("invalid dimension index"),
27        }
28    }
29
30    unsafe fn nth_unchecked(&self, n: usize) -> Self::T {
31        match n {
32            0 => self.x(),
33            1 => self.y(),
34            _ => unreachable_unchecked(),
35        }
36    }
37
38    fn x(&self) -> Self::T {
39        self.x
40    }
41
42    fn y(&self) -> Self::T {
43        self.y
44    }
45}
46
47impl CoordTrait for &Point {
48    type T = f64;
49
50    fn dim(&self) -> geo_traits::Dimensions {
51        geo_traits::Dimensions::Xy
52    }
53
54    fn nth_or_panic(&self, n: usize) -> Self::T {
55        match n {
56            0 => self.x(),
57            1 => self.y(),
58            _ => panic!("invalid dimension index"),
59        }
60    }
61
62    unsafe fn nth_unchecked(&self, n: usize) -> Self::T {
63        match n {
64            0 => self.x(),
65            1 => self.y(),
66            _ => unreachable_unchecked(),
67        }
68    }
69
70    fn x(&self) -> Self::T {
71        self.x
72    }
73
74    fn y(&self) -> Self::T {
75        self.y
76    }
77}
78
79impl PointTrait for Point {
80    type CoordType<'a>
81        = &'a Point
82    where
83        Self: 'a;
84
85    fn coord(&self) -> Option<Self::CoordType<'_>> {
86        Some(self)
87    }
88}
89
90impl PointTrait for &Point {
91    type CoordType<'a>
92        = &'a Point
93    where
94        Self: 'a;
95
96    fn coord(&self) -> Option<Self::CoordType<'_>> {
97        Some(self)
98    }
99}
100
101// Shapefile points can't be null, so we implement both traits on them
102impl CoordTrait for PointM {
103    type T = f64;
104
105    fn dim(&self) -> geo_traits::Dimensions {
106        if self.m <= NO_DATA {
107            geo_traits::Dimensions::Xy
108        } else {
109            geo_traits::Dimensions::Xym
110        }
111    }
112
113    fn nth_or_panic(&self, n: usize) -> Self::T {
114        match n {
115            0 => self.x(),
116            1 => self.y(),
117            2 => self.m,
118            _ => panic!("invalid dimension index"),
119        }
120    }
121
122    fn x(&self) -> Self::T {
123        self.x
124    }
125
126    fn y(&self) -> Self::T {
127        self.y
128    }
129}
130
131impl CoordTrait for &PointM {
132    type T = f64;
133
134    fn dim(&self) -> geo_traits::Dimensions {
135        if self.m <= NO_DATA {
136            geo_traits::Dimensions::Xy
137        } else {
138            geo_traits::Dimensions::Xym
139        }
140    }
141
142    fn nth_or_panic(&self, n: usize) -> Self::T {
143        match n {
144            0 => self.x(),
145            1 => self.y(),
146            2 => self.m,
147            _ => panic!("invalid dimension index"),
148        }
149    }
150
151    fn x(&self) -> Self::T {
152        self.x
153    }
154
155    fn y(&self) -> Self::T {
156        self.y
157    }
158}
159
160impl PointTrait for PointM {
161    type CoordType<'a>
162        = &'a PointM
163    where
164        Self: 'a;
165
166    fn coord(&self) -> Option<Self::CoordType<'_>> {
167        Some(self)
168    }
169}
170
171impl PointTrait for &PointM {
172    type CoordType<'a>
173        = &'a PointM
174    where
175        Self: 'a;
176
177    fn coord(&self) -> Option<Self::CoordType<'_>> {
178        Some(self)
179    }
180}
181
182// Shapefile points can't be null, so we implement both traits on them
183impl CoordTrait for PointZ {
184    type T = f64;
185
186    fn dim(&self) -> geo_traits::Dimensions {
187        if self.m <= NO_DATA {
188            geo_traits::Dimensions::Xyz
189        } else {
190            geo_traits::Dimensions::Xyzm
191        }
192    }
193
194    fn nth_or_panic(&self, n: usize) -> Self::T {
195        match n {
196            0 => self.x(),
197            1 => self.y(),
198            2 => self.z,
199            3 => {
200                if self.m > NO_DATA {
201                    self.m
202                } else {
203                    panic!("asked for 4th item from coordinate but this coordinate does not have 4 dimensions.")
204                }
205            }
206            _ => panic!("invalid dimension index"),
207        }
208    }
209
210    fn x(&self) -> Self::T {
211        self.x
212    }
213
214    fn y(&self) -> Self::T {
215        self.y
216    }
217}
218
219impl CoordTrait for &PointZ {
220    type T = f64;
221
222    fn dim(&self) -> geo_traits::Dimensions {
223        if self.m <= NO_DATA {
224            geo_traits::Dimensions::Xyz
225        } else {
226            geo_traits::Dimensions::Xyzm
227        }
228    }
229
230    fn nth_or_panic(&self, n: usize) -> Self::T {
231        match n {
232            0 => self.x(),
233            1 => self.y(),
234            2 => self.z,
235            3 => {
236                if self.m > NO_DATA {
237                    self.m
238                } else {
239                    panic!("asked for 4th item from coordinate but this coordinate does not have 4 dimensions.")
240                }
241            }
242            _ => panic!("invalid dimension index"),
243        }
244    }
245
246    fn x(&self) -> Self::T {
247        self.x
248    }
249
250    fn y(&self) -> Self::T {
251        self.y
252    }
253}
254
255impl PointTrait for PointZ {
256    type CoordType<'a>
257        = &'a PointZ
258    where
259        Self: 'a;
260
261    fn coord(&self) -> Option<Self::CoordType<'_>> {
262        Some(self)
263    }
264}
265
266impl PointTrait for &PointZ {
267    type CoordType<'a>
268        = &'a PointZ
269    where
270        Self: 'a;
271
272    fn coord(&self) -> Option<Self::CoordType<'_>> {
273        Some(self)
274    }
275}
276
277pub struct LineString<'a>(&'a [Point]);
278
279impl LineStringTrait for LineString<'_> {
280    type CoordType<'b>
281        = &'b Point
282    where
283        Self: 'b;
284
285    fn num_coords(&self) -> usize {
286        self.0.len()
287    }
288
289    unsafe fn coord_unchecked(&self, i: usize) -> Self::CoordType<'_> {
290        self.0.get_unchecked(i)
291    }
292}
293
294pub struct LineStringM<'a>(&'a [PointM]);
295
296impl LineStringTrait for LineStringM<'_> {
297    type CoordType<'b>
298        = &'b PointM
299    where
300        Self: 'b;
301
302    fn num_coords(&self) -> usize {
303        self.0.len()
304    }
305
306    unsafe fn coord_unchecked(&self, i: usize) -> Self::CoordType<'_> {
307        self.0.get_unchecked(i)
308    }
309}
310
311pub struct LineStringZ<'a>(&'a [PointZ]);
312
313impl LineStringTrait for LineStringZ<'_> {
314    type CoordType<'b>
315        = &'b PointZ
316    where
317        Self: 'b;
318
319    fn num_coords(&self) -> usize {
320        self.0.len()
321    }
322
323    unsafe fn coord_unchecked(&self, i: usize) -> Self::CoordType<'_> {
324        self.0.get_unchecked(i)
325    }
326}
327
328pub struct Polygon {
329    outer: Vec<Point>,
330    inner: Vec<Vec<Point>>,
331}
332
333impl<'a> PolygonTrait for &'a Polygon {
334    type RingType<'b>
335        = LineString<'a>
336    where
337        Self: 'b;
338
339    fn num_interiors(&self) -> usize {
340        self.inner.len()
341    }
342
343    fn exterior(&self) -> Option<Self::RingType<'_>> {
344        Some(LineString(&self.outer))
345    }
346
347    unsafe fn interior_unchecked(&self, i: usize) -> Self::RingType<'_> {
348        LineString(&self.inner[i])
349    }
350}
351
352pub struct PolygonM {
353    outer: Vec<PointM>,
354    inner: Vec<Vec<PointM>>,
355}
356
357impl<'a> PolygonTrait for &'a PolygonM {
358    type RingType<'b>
359        = LineStringM<'a>
360    where
361        Self: 'b;
362
363    fn num_interiors(&self) -> usize {
364        self.inner.len()
365    }
366
367    fn exterior(&self) -> Option<Self::RingType<'_>> {
368        Some(LineStringM(&self.outer))
369    }
370
371    unsafe fn interior_unchecked(&self, i: usize) -> Self::RingType<'_> {
372        LineStringM(&self.inner[i])
373    }
374}
375
376pub struct PolygonZ {
377    outer: Vec<PointZ>,
378    inner: Vec<Vec<PointZ>>,
379}
380
381impl<'a> PolygonTrait for &'a PolygonZ {
382    type RingType<'b>
383        = LineStringZ<'a>
384    where
385        Self: 'b;
386
387    fn num_interiors(&self) -> usize {
388        self.inner.len()
389    }
390
391    fn exterior(&self) -> Option<Self::RingType<'_>> {
392        Some(LineStringZ(&self.outer))
393    }
394
395    unsafe fn interior_unchecked(&self, i: usize) -> Self::RingType<'_> {
396        LineStringZ(&self.inner[i])
397    }
398}
399
400impl MultiPointTrait for Multipoint {
401    type InnerPointType<'b>
402        = &'b Point
403    where
404        Self: 'b;
405
406    fn num_points(&self) -> usize {
407        self.points().len()
408    }
409
410    unsafe fn point_unchecked(&self, i: usize) -> Self::PointType<'_> {
411        self.point(i).unwrap()
412    }
413}
414
415impl MultiPointTrait for MultipointM {
416    type InnerPointType<'b>
417        = &'b PointM
418    where
419        Self: 'b;
420
421    fn num_points(&self) -> usize {
422        self.points().len()
423    }
424
425    unsafe fn point_unchecked(&self, i: usize) -> Self::PointType<'_> {
426        self.point(i).unwrap()
427    }
428}
429
430impl MultiPointTrait for MultipointZ {
431    type InnerPointType<'b>
432        = &'b PointZ
433    where
434        Self: 'b;
435
436    fn num_points(&self) -> usize {
437        self.points().len()
438    }
439
440    unsafe fn point_unchecked(&self, i: usize) -> Self::PointType<'_> {
441        self.point(i).unwrap()
442    }
443}
444
445impl MultiLineStringTrait for Polyline {
446    type InnerLineStringType<'a>
447        = LineString<'a>
448    where
449        Self: 'a;
450
451    fn num_line_strings(&self) -> usize {
452        self.parts().len()
453    }
454
455    unsafe fn line_string_unchecked(&self, i: usize) -> Self::LineStringType<'_> {
456        LineString(self.part(i).unwrap())
457    }
458}
459
460impl MultiLineStringTrait for PolylineM {
461    type InnerLineStringType<'a>
462        = LineStringM<'a>
463    where
464        Self: 'a;
465
466    fn num_line_strings(&self) -> usize {
467        self.parts().len()
468    }
469
470    unsafe fn line_string_unchecked(&self, i: usize) -> Self::LineStringType<'_> {
471        LineStringM(self.part(i).unwrap())
472    }
473}
474
475impl MultiLineStringTrait for PolylineZ {
476    type InnerLineStringType<'a>
477        = LineStringZ<'a>
478    where
479        Self: 'a;
480
481    fn num_line_strings(&self) -> usize {
482        self.parts().len()
483    }
484
485    unsafe fn line_string_unchecked(&self, i: usize) -> Self::LineStringType<'_> {
486        LineStringZ(self.part(i).unwrap())
487    }
488}
489
490pub struct MultiPolygon(Vec<Polygon>);
491
492impl TryFrom<crate::Polygon> for MultiPolygon {
493    type Error = crate::Error;
494
495    fn try_from(geom: crate::Polygon) -> Result<Self, Self::Error> {
496        let mut last_poly = None;
497        let mut polygons = Vec::new();
498        for ring in geom.into_inner() {
499            match ring {
500                PolygonRing::Outer(points) => {
501                    if let Some(poly) = last_poly.take() {
502                        polygons.push(poly);
503                    }
504                    last_poly = Some(Polygon {
505                        outer: points,
506                        inner: vec![],
507                    });
508                }
509                PolygonRing::Inner(points) => {
510                    if let Some(poly) = last_poly.as_mut() {
511                        poly.inner.push(points);
512                    } else {
513                        return Err(crate::Error::OrphanedInnerRing);
514                    }
515                }
516            }
517        }
518
519        if let Some(poly) = last_poly.take() {
520            polygons.push(poly);
521        }
522
523        Ok(Self(polygons))
524    }
525}
526
527impl MultiPolygonTrait for MultiPolygon {
528    type InnerPolygonType<'a> = &'a Polygon;
529
530    fn num_polygons(&self) -> usize {
531        self.0.len()
532    }
533
534    unsafe fn polygon_unchecked(&self, i: usize) -> Self::PolygonType<'_> {
535        &self.0[i]
536    }
537}
538
539pub struct MultiPolygonM(Vec<PolygonM>);
540
541impl TryFrom<crate::PolygonM> for MultiPolygonM {
542    type Error = crate::Error;
543
544    fn try_from(geom: crate::PolygonM) -> Result<Self, Self::Error> {
545        let mut last_poly = None;
546        let mut polygons = Vec::new();
547        for ring in geom.into_inner() {
548            match ring {
549                PolygonRing::Outer(points) => {
550                    if let Some(poly) = last_poly.take() {
551                        polygons.push(poly);
552                    }
553                    last_poly = Some(PolygonM {
554                        outer: points,
555                        inner: vec![],
556                    });
557                }
558                PolygonRing::Inner(points) => {
559                    if let Some(poly) = last_poly.as_mut() {
560                        poly.inner.push(points);
561                    } else {
562                        return Err(crate::Error::OrphanedInnerRing);
563                    }
564                }
565            }
566        }
567
568        if let Some(poly) = last_poly.take() {
569            polygons.push(poly);
570        }
571
572        Ok(Self(polygons))
573    }
574}
575
576impl MultiPolygonTrait for MultiPolygonM {
577    type InnerPolygonType<'a> = &'a PolygonM;
578
579    fn num_polygons(&self) -> usize {
580        self.0.len()
581    }
582
583    unsafe fn polygon_unchecked(&self, i: usize) -> Self::PolygonType<'_> {
584        &self.0[i]
585    }
586}
587
588pub struct MultiPolygonZ(Vec<PolygonZ>);
589
590impl TryFrom<crate::PolygonZ> for MultiPolygonZ {
591    type Error = crate::Error;
592
593    fn try_from(geom: crate::PolygonZ) -> Result<Self, Self::Error> {
594        let mut last_poly = None;
595        let mut polygons = Vec::new();
596        for ring in geom.into_inner() {
597            match ring {
598                PolygonRing::Outer(points) => {
599                    if let Some(poly) = last_poly.take() {
600                        polygons.push(poly);
601                    }
602                    last_poly = Some(PolygonZ {
603                        outer: points,
604                        inner: vec![],
605                    });
606                }
607                PolygonRing::Inner(points) => {
608                    if let Some(poly) = last_poly.as_mut() {
609                        poly.inner.push(points);
610                    } else {
611                        return Err(crate::Error::OrphanedInnerRing);
612                    }
613                }
614            }
615        }
616
617        if let Some(poly) = last_poly.take() {
618            polygons.push(poly);
619        }
620
621        Ok(Self(polygons))
622    }
623}
624
625impl MultiPolygonTrait for MultiPolygonZ {
626    type InnerPolygonType<'a> = &'a PolygonZ;
627
628    fn num_polygons(&self) -> usize {
629        self.0.len()
630    }
631
632    unsafe fn polygon_unchecked(&self, i: usize) -> Self::PolygonType<'_> {
633        &self.0[i]
634    }
635}
636
637/////////////////////////////////
638// Geometry trait implementations
639
640impl GeometryTrait for Point {
641    type T = f64;
642    type PointType<'b>
643        = Self
644    where
645        Self: 'b;
646    type LineStringType<'b>
647        = UnimplementedLineString<Self::T>
648    where
649        Self: 'b;
650    type PolygonType<'b>
651        = UnimplementedPolygon<Self::T>
652    where
653        Self: 'b;
654    type MultiPointType<'b>
655        = UnimplementedMultiPoint<Self::T>
656    where
657        Self: 'b;
658    type MultiLineStringType<'b>
659        = UnimplementedMultiLineString<Self::T>
660    where
661        Self: 'b;
662    type MultiPolygonType<'b>
663        = UnimplementedMultiPolygon<Self::T>
664    where
665        Self: 'b;
666    type GeometryCollectionType<'b>
667        = geo_traits::UnimplementedGeometryCollection<Self::T>
668    where
669        Self: 'b;
670    type RectType<'b>
671        = geo_traits::UnimplementedRect<f64>
672    where
673        Self: 'b;
674    type LineType<'b>
675        = geo_traits::UnimplementedLine<f64>
676    where
677        Self: 'b;
678    type TriangleType<'b>
679        = geo_traits::UnimplementedTriangle<f64>
680    where
681        Self: 'b;
682
683    fn dim(&self) -> geo_traits::Dimensions {
684        geo_traits::Dimensions::Xy
685    }
686
687    fn as_type(
688        &self,
689    ) -> geo_traits::GeometryType<
690        '_,
691        Self::PointType<'_>,
692        Self::LineStringType<'_>,
693        Self::PolygonType<'_>,
694        Self::MultiPointType<'_>,
695        Self::MultiLineStringType<'_>,
696        Self::MultiPolygonType<'_>,
697        Self::GeometryCollectionType<'_>,
698        Self::RectType<'_>,
699        Self::TriangleType<'_>,
700        Self::LineType<'_>,
701    > {
702        geo_traits::GeometryType::Point(self)
703    }
704}
705
706impl GeometryTrait for &Point {
707    type T = f64;
708    type PointType<'b>
709        = Self
710    where
711        Self: 'b;
712    type LineStringType<'b>
713        = UnimplementedLineString<Self::T>
714    where
715        Self: 'b;
716    type PolygonType<'b>
717        = UnimplementedPolygon<Self::T>
718    where
719        Self: 'b;
720    type MultiPointType<'b>
721        = UnimplementedMultiPoint<Self::T>
722    where
723        Self: 'b;
724    type MultiLineStringType<'b>
725        = UnimplementedMultiLineString<Self::T>
726    where
727        Self: 'b;
728    type MultiPolygonType<'b>
729        = UnimplementedMultiPolygon<Self::T>
730    where
731        Self: 'b;
732    type GeometryCollectionType<'b>
733        = geo_traits::UnimplementedGeometryCollection<Self::T>
734    where
735        Self: 'b;
736    type RectType<'b>
737        = geo_traits::UnimplementedRect<f64>
738    where
739        Self: 'b;
740    type LineType<'b>
741        = geo_traits::UnimplementedLine<f64>
742    where
743        Self: 'b;
744    type TriangleType<'b>
745        = geo_traits::UnimplementedTriangle<f64>
746    where
747        Self: 'b;
748
749    fn dim(&self) -> geo_traits::Dimensions {
750        geo_traits::Dimensions::Xy
751    }
752
753    fn as_type(
754        &self,
755    ) -> geo_traits::GeometryType<
756        '_,
757        Self::PointType<'_>,
758        Self::LineStringType<'_>,
759        Self::PolygonType<'_>,
760        Self::MultiPointType<'_>,
761        Self::MultiLineStringType<'_>,
762        Self::MultiPolygonType<'_>,
763        Self::GeometryCollectionType<'_>,
764        Self::RectType<'_>,
765        Self::TriangleType<'_>,
766        Self::LineType<'_>,
767    > {
768        geo_traits::GeometryType::Point(self)
769    }
770}
771
772impl GeometryTrait for PointM {
773    type T = f64;
774    type PointType<'b>
775        = Self
776    where
777        Self: 'b;
778    type LineStringType<'b>
779        = UnimplementedLineString<Self::T>
780    where
781        Self: 'b;
782    type PolygonType<'b>
783        = UnimplementedPolygon<Self::T>
784    where
785        Self: 'b;
786    type MultiPointType<'b>
787        = UnimplementedMultiPoint<Self::T>
788    where
789        Self: 'b;
790    type MultiLineStringType<'b>
791        = UnimplementedMultiLineString<Self::T>
792    where
793        Self: 'b;
794    type MultiPolygonType<'b>
795        = UnimplementedMultiPolygon<Self::T>
796    where
797        Self: 'b;
798    type GeometryCollectionType<'b>
799        = geo_traits::UnimplementedGeometryCollection<Self::T>
800    where
801        Self: 'b;
802    type RectType<'b>
803        = geo_traits::UnimplementedRect<f64>
804    where
805        Self: 'b;
806    type LineType<'b>
807        = geo_traits::UnimplementedLine<f64>
808    where
809        Self: 'b;
810    type TriangleType<'b>
811        = geo_traits::UnimplementedTriangle<f64>
812    where
813        Self: 'b;
814
815    fn dim(&self) -> geo_traits::Dimensions {
816        if self.m <= NO_DATA {
817            geo_traits::Dimensions::Xy
818        } else {
819            geo_traits::Dimensions::Xym
820        }
821    }
822
823    fn as_type(
824        &self,
825    ) -> geo_traits::GeometryType<
826        '_,
827        Self::PointType<'_>,
828        Self::LineStringType<'_>,
829        Self::PolygonType<'_>,
830        Self::MultiPointType<'_>,
831        Self::MultiLineStringType<'_>,
832        Self::MultiPolygonType<'_>,
833        Self::GeometryCollectionType<'_>,
834        Self::RectType<'_>,
835        Self::TriangleType<'_>,
836        Self::LineType<'_>,
837    > {
838        geo_traits::GeometryType::Point(self)
839    }
840}
841
842impl GeometryTrait for &PointM {
843    type T = f64;
844    type PointType<'b>
845        = Self
846    where
847        Self: 'b;
848    type LineStringType<'b>
849        = UnimplementedLineString<Self::T>
850    where
851        Self: 'b;
852    type PolygonType<'b>
853        = UnimplementedPolygon<Self::T>
854    where
855        Self: 'b;
856    type MultiPointType<'b>
857        = UnimplementedMultiPoint<Self::T>
858    where
859        Self: 'b;
860    type MultiLineStringType<'b>
861        = UnimplementedMultiLineString<Self::T>
862    where
863        Self: 'b;
864    type MultiPolygonType<'b>
865        = UnimplementedMultiPolygon<Self::T>
866    where
867        Self: 'b;
868    type GeometryCollectionType<'b>
869        = geo_traits::UnimplementedGeometryCollection<Self::T>
870    where
871        Self: 'b;
872    type RectType<'b>
873        = geo_traits::UnimplementedRect<f64>
874    where
875        Self: 'b;
876    type LineType<'b>
877        = geo_traits::UnimplementedLine<f64>
878    where
879        Self: 'b;
880    type TriangleType<'b>
881        = geo_traits::UnimplementedTriangle<f64>
882    where
883        Self: 'b;
884
885    fn dim(&self) -> geo_traits::Dimensions {
886        if self.m <= NO_DATA {
887            geo_traits::Dimensions::Xy
888        } else {
889            geo_traits::Dimensions::Xym
890        }
891    }
892
893    fn as_type(
894        &self,
895    ) -> geo_traits::GeometryType<
896        '_,
897        Self::PointType<'_>,
898        Self::LineStringType<'_>,
899        Self::PolygonType<'_>,
900        Self::MultiPointType<'_>,
901        Self::MultiLineStringType<'_>,
902        Self::MultiPolygonType<'_>,
903        Self::GeometryCollectionType<'_>,
904        Self::RectType<'_>,
905        Self::TriangleType<'_>,
906        Self::LineType<'_>,
907    > {
908        geo_traits::GeometryType::Point(self)
909    }
910}
911
912impl GeometryTrait for PointZ {
913    type T = f64;
914    type PointType<'b>
915        = Self
916    where
917        Self: 'b;
918    type LineStringType<'b>
919        = UnimplementedLineString<Self::T>
920    where
921        Self: 'b;
922    type PolygonType<'b>
923        = UnimplementedPolygon<Self::T>
924    where
925        Self: 'b;
926    type MultiPointType<'b>
927        = UnimplementedMultiPoint<Self::T>
928    where
929        Self: 'b;
930    type MultiLineStringType<'b>
931        = UnimplementedMultiLineString<Self::T>
932    where
933        Self: 'b;
934    type MultiPolygonType<'b>
935        = UnimplementedMultiPolygon<Self::T>
936    where
937        Self: 'b;
938    type GeometryCollectionType<'b>
939        = geo_traits::UnimplementedGeometryCollection<Self::T>
940    where
941        Self: 'b;
942    type RectType<'b>
943        = geo_traits::UnimplementedRect<f64>
944    where
945        Self: 'b;
946    type LineType<'b>
947        = geo_traits::UnimplementedLine<f64>
948    where
949        Self: 'b;
950    type TriangleType<'b>
951        = geo_traits::UnimplementedTriangle<f64>
952    where
953        Self: 'b;
954
955    fn dim(&self) -> geo_traits::Dimensions {
956        if self.m <= NO_DATA {
957            geo_traits::Dimensions::Xyz
958        } else {
959            geo_traits::Dimensions::Xyzm
960        }
961    }
962
963    fn as_type(
964        &self,
965    ) -> geo_traits::GeometryType<
966        '_,
967        Self::PointType<'_>,
968        Self::LineStringType<'_>,
969        Self::PolygonType<'_>,
970        Self::MultiPointType<'_>,
971        Self::MultiLineStringType<'_>,
972        Self::MultiPolygonType<'_>,
973        Self::GeometryCollectionType<'_>,
974        Self::RectType<'_>,
975        Self::TriangleType<'_>,
976        Self::LineType<'_>,
977    > {
978        geo_traits::GeometryType::Point(self)
979    }
980}
981
982impl GeometryTrait for &PointZ {
983    type T = f64;
984    type PointType<'b>
985        = Self
986    where
987        Self: 'b;
988    type LineStringType<'b>
989        = UnimplementedLineString<Self::T>
990    where
991        Self: 'b;
992    type PolygonType<'b>
993        = UnimplementedPolygon<Self::T>
994    where
995        Self: 'b;
996    type MultiPointType<'b>
997        = UnimplementedMultiPoint<Self::T>
998    where
999        Self: 'b;
1000    type MultiLineStringType<'b>
1001        = UnimplementedMultiLineString<Self::T>
1002    where
1003        Self: 'b;
1004    type MultiPolygonType<'b>
1005        = UnimplementedMultiPolygon<Self::T>
1006    where
1007        Self: 'b;
1008    type GeometryCollectionType<'b>
1009        = geo_traits::UnimplementedGeometryCollection<Self::T>
1010    where
1011        Self: 'b;
1012    type RectType<'b>
1013        = geo_traits::UnimplementedRect<f64>
1014    where
1015        Self: 'b;
1016    type LineType<'b>
1017        = geo_traits::UnimplementedLine<f64>
1018    where
1019        Self: 'b;
1020    type TriangleType<'b>
1021        = geo_traits::UnimplementedTriangle<f64>
1022    where
1023        Self: 'b;
1024
1025    fn dim(&self) -> geo_traits::Dimensions {
1026        if self.m <= NO_DATA {
1027            geo_traits::Dimensions::Xyz
1028        } else {
1029            geo_traits::Dimensions::Xyzm
1030        }
1031    }
1032
1033    fn as_type(
1034        &self,
1035    ) -> geo_traits::GeometryType<
1036        '_,
1037        Self::PointType<'_>,
1038        Self::LineStringType<'_>,
1039        Self::PolygonType<'_>,
1040        Self::MultiPointType<'_>,
1041        Self::MultiLineStringType<'_>,
1042        Self::MultiPolygonType<'_>,
1043        Self::GeometryCollectionType<'_>,
1044        Self::RectType<'_>,
1045        Self::TriangleType<'_>,
1046        Self::LineType<'_>,
1047    > {
1048        geo_traits::GeometryType::Point(self)
1049    }
1050}
1051
1052impl<'a> GeometryTrait for LineString<'a> {
1053    type T = f64;
1054    type PointType<'b>
1055        = UnimplementedPoint<Self::T>
1056    where
1057        Self: 'b;
1058    type LineStringType<'b>
1059        = Self
1060    where
1061        Self: 'b;
1062    type PolygonType<'b>
1063        = UnimplementedPolygon<Self::T>
1064    where
1065        Self: 'b;
1066    type MultiPointType<'b>
1067        = UnimplementedMultiPoint<Self::T>
1068    where
1069        Self: 'b;
1070    type MultiLineStringType<'b>
1071        = UnimplementedMultiLineString<Self::T>
1072    where
1073        Self: 'b;
1074    type MultiPolygonType<'b>
1075        = UnimplementedMultiPolygon<Self::T>
1076    where
1077        Self: 'b;
1078    type GeometryCollectionType<'b>
1079        = geo_traits::UnimplementedGeometryCollection<Self::T>
1080    where
1081        Self: 'b;
1082    type RectType<'b>
1083        = geo_traits::UnimplementedRect<f64>
1084    where
1085        Self: 'b;
1086    type LineType<'b>
1087        = geo_traits::UnimplementedLine<f64>
1088    where
1089        Self: 'b;
1090    type TriangleType<'b>
1091        = geo_traits::UnimplementedTriangle<f64>
1092    where
1093        Self: 'b;
1094
1095    fn dim(&self) -> geo_traits::Dimensions {
1096        geo_traits::Dimensions::Xy
1097    }
1098
1099    fn as_type(
1100        &self,
1101    ) -> geo_traits::GeometryType<
1102        '_,
1103        Self::PointType<'_>,
1104        Self::LineStringType<'_>,
1105        Self::PolygonType<'_>,
1106        Self::MultiPointType<'_>,
1107        Self::MultiLineStringType<'_>,
1108        Self::MultiPolygonType<'_>,
1109        Self::GeometryCollectionType<'_>,
1110        Self::RectType<'_>,
1111        Self::TriangleType<'_>,
1112        Self::LineType<'_>,
1113    > {
1114        geo_traits::GeometryType::LineString(self)
1115    }
1116}
1117
1118impl<'a> GeometryTrait for LineStringM<'a> {
1119    type T = f64;
1120    type PointType<'b>
1121        = UnimplementedPoint<Self::T>
1122    where
1123        Self: 'b;
1124    type LineStringType<'b>
1125        = Self
1126    where
1127        Self: 'b;
1128    type PolygonType<'b>
1129        = UnimplementedPolygon<Self::T>
1130    where
1131        Self: 'b;
1132    type MultiPointType<'b>
1133        = UnimplementedMultiPoint<Self::T>
1134    where
1135        Self: 'b;
1136    type MultiLineStringType<'b>
1137        = UnimplementedMultiLineString<Self::T>
1138    where
1139        Self: 'b;
1140    type MultiPolygonType<'b>
1141        = UnimplementedMultiPolygon<Self::T>
1142    where
1143        Self: 'b;
1144    type GeometryCollectionType<'b>
1145        = geo_traits::UnimplementedGeometryCollection<Self::T>
1146    where
1147        Self: 'b;
1148    type RectType<'b>
1149        = geo_traits::UnimplementedRect<f64>
1150    where
1151        Self: 'b;
1152    type LineType<'b>
1153        = geo_traits::UnimplementedLine<f64>
1154    where
1155        Self: 'b;
1156    type TriangleType<'b>
1157        = geo_traits::UnimplementedTriangle<f64>
1158    where
1159        Self: 'b;
1160
1161    fn dim(&self) -> geo_traits::Dimensions {
1162        geo_traits::Dimensions::Xym
1163    }
1164
1165    fn as_type(
1166        &self,
1167    ) -> geo_traits::GeometryType<
1168        '_,
1169        Self::PointType<'_>,
1170        Self::LineStringType<'_>,
1171        Self::PolygonType<'_>,
1172        Self::MultiPointType<'_>,
1173        Self::MultiLineStringType<'_>,
1174        Self::MultiPolygonType<'_>,
1175        Self::GeometryCollectionType<'_>,
1176        Self::RectType<'_>,
1177        Self::TriangleType<'_>,
1178        Self::LineType<'_>,
1179    > {
1180        geo_traits::GeometryType::LineString(self)
1181    }
1182}
1183
1184impl<'a> GeometryTrait for LineStringZ<'a> {
1185    type T = f64;
1186    type PointType<'b>
1187        = UnimplementedPoint<Self::T>
1188    where
1189        Self: 'b;
1190    type LineStringType<'b>
1191        = Self
1192    where
1193        Self: 'b;
1194    type PolygonType<'b>
1195        = UnimplementedPolygon<Self::T>
1196    where
1197        Self: 'b;
1198    type MultiPointType<'b>
1199        = UnimplementedMultiPoint<Self::T>
1200    where
1201        Self: 'b;
1202    type MultiLineStringType<'b>
1203        = UnimplementedMultiLineString<Self::T>
1204    where
1205        Self: 'b;
1206    type MultiPolygonType<'b>
1207        = UnimplementedMultiPolygon<Self::T>
1208    where
1209        Self: 'b;
1210    type GeometryCollectionType<'b>
1211        = geo_traits::UnimplementedGeometryCollection<Self::T>
1212    where
1213        Self: 'b;
1214    type RectType<'b>
1215        = geo_traits::UnimplementedRect<f64>
1216    where
1217        Self: 'b;
1218    type LineType<'b>
1219        = geo_traits::UnimplementedLine<f64>
1220    where
1221        Self: 'b;
1222    type TriangleType<'b>
1223        = geo_traits::UnimplementedTriangle<f64>
1224    where
1225        Self: 'b;
1226
1227    fn dim(&self) -> geo_traits::Dimensions {
1228        // Check the first underlying coordinate to check if it's XYZ or XYZM
1229        self.0
1230            .first()
1231            .map(CoordTrait::dim)
1232            .unwrap_or(geo_traits::Dimensions::Xyz)
1233    }
1234
1235    fn as_type(
1236        &self,
1237    ) -> geo_traits::GeometryType<
1238        '_,
1239        Self::PointType<'_>,
1240        Self::LineStringType<'_>,
1241        Self::PolygonType<'_>,
1242        Self::MultiPointType<'_>,
1243        Self::MultiLineStringType<'_>,
1244        Self::MultiPolygonType<'_>,
1245        Self::GeometryCollectionType<'_>,
1246        Self::RectType<'_>,
1247        Self::TriangleType<'_>,
1248        Self::LineType<'_>,
1249    > {
1250        geo_traits::GeometryType::LineString(self)
1251    }
1252}
1253
1254impl GeometryTrait for &'_ Polygon {
1255    type T = f64;
1256    type PointType<'b>
1257        = UnimplementedPoint<Self::T>
1258    where
1259        Self: 'b;
1260    type LineStringType<'b>
1261        = UnimplementedLineString<Self::T>
1262    where
1263        Self: 'b;
1264    type PolygonType<'b>
1265        = Self
1266    where
1267        Self: 'b;
1268    type MultiPointType<'b>
1269        = UnimplementedMultiPoint<Self::T>
1270    where
1271        Self: 'b;
1272    type MultiLineStringType<'b>
1273        = UnimplementedMultiLineString<Self::T>
1274    where
1275        Self: 'b;
1276    type MultiPolygonType<'b>
1277        = UnimplementedMultiPolygon<Self::T>
1278    where
1279        Self: 'b;
1280    type GeometryCollectionType<'b>
1281        = geo_traits::UnimplementedGeometryCollection<Self::T>
1282    where
1283        Self: 'b;
1284    type RectType<'b>
1285        = geo_traits::UnimplementedRect<f64>
1286    where
1287        Self: 'b;
1288    type LineType<'b>
1289        = geo_traits::UnimplementedLine<f64>
1290    where
1291        Self: 'b;
1292    type TriangleType<'b>
1293        = geo_traits::UnimplementedTriangle<f64>
1294    where
1295        Self: 'b;
1296
1297    fn dim(&self) -> geo_traits::Dimensions {
1298        geo_traits::Dimensions::Xy
1299    }
1300
1301    fn as_type(
1302        &self,
1303    ) -> geo_traits::GeometryType<
1304        '_,
1305        Self::PointType<'_>,
1306        Self::LineStringType<'_>,
1307        Self::PolygonType<'_>,
1308        Self::MultiPointType<'_>,
1309        Self::MultiLineStringType<'_>,
1310        Self::MultiPolygonType<'_>,
1311        Self::GeometryCollectionType<'_>,
1312        Self::RectType<'_>,
1313        Self::TriangleType<'_>,
1314        Self::LineType<'_>,
1315    > {
1316        geo_traits::GeometryType::Polygon(self)
1317    }
1318}
1319
1320impl GeometryTrait for &'_ PolygonM {
1321    type T = f64;
1322    type PointType<'b>
1323        = UnimplementedPoint<Self::T>
1324    where
1325        Self: 'b;
1326    type LineStringType<'b>
1327        = UnimplementedLineString<Self::T>
1328    where
1329        Self: 'b;
1330    type PolygonType<'b>
1331        = Self
1332    where
1333        Self: 'b;
1334    type MultiPointType<'b>
1335        = UnimplementedMultiPoint<Self::T>
1336    where
1337        Self: 'b;
1338    type MultiLineStringType<'b>
1339        = UnimplementedMultiLineString<Self::T>
1340    where
1341        Self: 'b;
1342    type MultiPolygonType<'b>
1343        = UnimplementedMultiPolygon<Self::T>
1344    where
1345        Self: 'b;
1346    type GeometryCollectionType<'b>
1347        = geo_traits::UnimplementedGeometryCollection<Self::T>
1348    where
1349        Self: 'b;
1350    type RectType<'b>
1351        = geo_traits::UnimplementedRect<f64>
1352    where
1353        Self: 'b;
1354    type LineType<'b>
1355        = geo_traits::UnimplementedLine<f64>
1356    where
1357        Self: 'b;
1358    type TriangleType<'b>
1359        = geo_traits::UnimplementedTriangle<f64>
1360    where
1361        Self: 'b;
1362
1363    fn dim(&self) -> geo_traits::Dimensions {
1364        geo_traits::Dimensions::Xym
1365    }
1366
1367    fn as_type(
1368        &self,
1369    ) -> geo_traits::GeometryType<
1370        '_,
1371        Self::PointType<'_>,
1372        Self::LineStringType<'_>,
1373        Self::PolygonType<'_>,
1374        Self::MultiPointType<'_>,
1375        Self::MultiLineStringType<'_>,
1376        Self::MultiPolygonType<'_>,
1377        Self::GeometryCollectionType<'_>,
1378        Self::RectType<'_>,
1379        Self::TriangleType<'_>,
1380        Self::LineType<'_>,
1381    > {
1382        geo_traits::GeometryType::Polygon(self)
1383    }
1384}
1385
1386impl GeometryTrait for &'_ PolygonZ {
1387    type T = f64;
1388    type PointType<'b>
1389        = UnimplementedPoint<Self::T>
1390    where
1391        Self: 'b;
1392    type LineStringType<'b>
1393        = UnimplementedLineString<Self::T>
1394    where
1395        Self: 'b;
1396    type PolygonType<'b>
1397        = Self
1398    where
1399        Self: 'b;
1400    type MultiPointType<'b>
1401        = UnimplementedMultiPoint<Self::T>
1402    where
1403        Self: 'b;
1404    type MultiLineStringType<'b>
1405        = UnimplementedMultiLineString<Self::T>
1406    where
1407        Self: 'b;
1408    type MultiPolygonType<'b>
1409        = UnimplementedMultiPolygon<Self::T>
1410    where
1411        Self: 'b;
1412    type GeometryCollectionType<'b>
1413        = geo_traits::UnimplementedGeometryCollection<Self::T>
1414    where
1415        Self: 'b;
1416    type RectType<'b>
1417        = geo_traits::UnimplementedRect<f64>
1418    where
1419        Self: 'b;
1420    type LineType<'b>
1421        = geo_traits::UnimplementedLine<f64>
1422    where
1423        Self: 'b;
1424    type TriangleType<'b>
1425        = geo_traits::UnimplementedTriangle<f64>
1426    where
1427        Self: 'b;
1428
1429    fn dim(&self) -> geo_traits::Dimensions {
1430        // Check the first coord of the outer ring to check if it's XYZ or XYZM
1431        self.outer
1432            .first()
1433            .map(CoordTrait::dim)
1434            .unwrap_or(geo_traits::Dimensions::Xyz)
1435    }
1436
1437    fn as_type(
1438        &self,
1439    ) -> geo_traits::GeometryType<
1440        '_,
1441        Self::PointType<'_>,
1442        Self::LineStringType<'_>,
1443        Self::PolygonType<'_>,
1444        Self::MultiPointType<'_>,
1445        Self::MultiLineStringType<'_>,
1446        Self::MultiPolygonType<'_>,
1447        Self::GeometryCollectionType<'_>,
1448        Self::RectType<'_>,
1449        Self::TriangleType<'_>,
1450        Self::LineType<'_>,
1451    > {
1452        geo_traits::GeometryType::Polygon(self)
1453    }
1454}
1455
1456impl GeometryTrait for Multipoint {
1457    type T = f64;
1458    type PointType<'b>
1459        = &'b Point
1460    where
1461        Self: 'b;
1462    type LineStringType<'b>
1463        = UnimplementedLineString<Self::T>
1464    where
1465        Self: 'b;
1466    type PolygonType<'b>
1467        = UnimplementedPolygon<Self::T>
1468    where
1469        Self: 'b;
1470    type MultiPointType<'b>
1471        = Self
1472    where
1473        Self: 'b;
1474    type MultiLineStringType<'b>
1475        = UnimplementedMultiLineString<Self::T>
1476    where
1477        Self: 'b;
1478    type MultiPolygonType<'b>
1479        = UnimplementedMultiPolygon<Self::T>
1480    where
1481        Self: 'b;
1482    type GeometryCollectionType<'b>
1483        = geo_traits::UnimplementedGeometryCollection<Self::T>
1484    where
1485        Self: 'b;
1486    type RectType<'b>
1487        = geo_traits::UnimplementedRect<f64>
1488    where
1489        Self: 'b;
1490    type LineType<'b>
1491        = geo_traits::UnimplementedLine<f64>
1492    where
1493        Self: 'b;
1494    type TriangleType<'b>
1495        = geo_traits::UnimplementedTriangle<f64>
1496    where
1497        Self: 'b;
1498
1499    fn dim(&self) -> geo_traits::Dimensions {
1500        geo_traits::Dimensions::Xy
1501    }
1502
1503    fn as_type(
1504        &self,
1505    ) -> geo_traits::GeometryType<
1506        '_,
1507        Self::PointType<'_>,
1508        Self::LineStringType<'_>,
1509        Self::PolygonType<'_>,
1510        Self::MultiPointType<'_>,
1511        Self::MultiLineStringType<'_>,
1512        Self::MultiPolygonType<'_>,
1513        Self::GeometryCollectionType<'_>,
1514        Self::RectType<'_>,
1515        Self::TriangleType<'_>,
1516        Self::LineType<'_>,
1517    > {
1518        geo_traits::GeometryType::MultiPoint(self)
1519    }
1520}
1521
1522impl GeometryTrait for MultipointM {
1523    type T = f64;
1524    type PointType<'b>
1525        = &'b PointM
1526    where
1527        Self: 'b;
1528    type LineStringType<'b>
1529        = UnimplementedLineString<Self::T>
1530    where
1531        Self: 'b;
1532    type PolygonType<'b>
1533        = UnimplementedPolygon<Self::T>
1534    where
1535        Self: 'b;
1536    type MultiPointType<'b>
1537        = Self
1538    where
1539        Self: 'b;
1540    type MultiLineStringType<'b>
1541        = UnimplementedMultiLineString<Self::T>
1542    where
1543        Self: 'b;
1544    type MultiPolygonType<'b>
1545        = UnimplementedMultiPolygon<Self::T>
1546    where
1547        Self: 'b;
1548    type GeometryCollectionType<'b>
1549        = geo_traits::UnimplementedGeometryCollection<Self::T>
1550    where
1551        Self: 'b;
1552    type RectType<'b>
1553        = geo_traits::UnimplementedRect<f64>
1554    where
1555        Self: 'b;
1556    type LineType<'b>
1557        = geo_traits::UnimplementedLine<f64>
1558    where
1559        Self: 'b;
1560    type TriangleType<'b>
1561        = geo_traits::UnimplementedTriangle<f64>
1562    where
1563        Self: 'b;
1564
1565    fn dim(&self) -> geo_traits::Dimensions {
1566        geo_traits::Dimensions::Xym
1567    }
1568
1569    fn as_type(
1570        &self,
1571    ) -> geo_traits::GeometryType<
1572        '_,
1573        Self::PointType<'_>,
1574        Self::LineStringType<'_>,
1575        Self::PolygonType<'_>,
1576        Self::MultiPointType<'_>,
1577        Self::MultiLineStringType<'_>,
1578        Self::MultiPolygonType<'_>,
1579        Self::GeometryCollectionType<'_>,
1580        Self::RectType<'_>,
1581        Self::TriangleType<'_>,
1582        Self::LineType<'_>,
1583    > {
1584        geo_traits::GeometryType::MultiPoint(self)
1585    }
1586}
1587
1588impl GeometryTrait for MultipointZ {
1589    type T = f64;
1590    type PointType<'b>
1591        = &'b PointZ
1592    where
1593        Self: 'b;
1594    type LineStringType<'b>
1595        = UnimplementedLineString<Self::T>
1596    where
1597        Self: 'b;
1598    type PolygonType<'b>
1599        = UnimplementedPolygon<Self::T>
1600    where
1601        Self: 'b;
1602    type MultiPointType<'b>
1603        = Self
1604    where
1605        Self: 'b;
1606    type MultiLineStringType<'b>
1607        = UnimplementedMultiLineString<Self::T>
1608    where
1609        Self: 'b;
1610    type MultiPolygonType<'b>
1611        = UnimplementedMultiPolygon<Self::T>
1612    where
1613        Self: 'b;
1614    type GeometryCollectionType<'b>
1615        = geo_traits::UnimplementedGeometryCollection<Self::T>
1616    where
1617        Self: 'b;
1618    type RectType<'b>
1619        = geo_traits::UnimplementedRect<f64>
1620    where
1621        Self: 'b;
1622    type LineType<'b>
1623        = geo_traits::UnimplementedLine<f64>
1624    where
1625        Self: 'b;
1626    type TriangleType<'b>
1627        = geo_traits::UnimplementedTriangle<f64>
1628    where
1629        Self: 'b;
1630
1631    fn dim(&self) -> geo_traits::Dimensions {
1632        // Check the first point to check if it's XYZ or XYZM
1633        self.points
1634            .first()
1635            .map(CoordTrait::dim)
1636            .unwrap_or(geo_traits::Dimensions::Xyz)
1637    }
1638
1639    fn as_type(
1640        &self,
1641    ) -> geo_traits::GeometryType<
1642        '_,
1643        Self::PointType<'_>,
1644        Self::LineStringType<'_>,
1645        Self::PolygonType<'_>,
1646        Self::MultiPointType<'_>,
1647        Self::MultiLineStringType<'_>,
1648        Self::MultiPolygonType<'_>,
1649        Self::GeometryCollectionType<'_>,
1650        Self::RectType<'_>,
1651        Self::TriangleType<'_>,
1652        Self::LineType<'_>,
1653    > {
1654        geo_traits::GeometryType::MultiPoint(self)
1655    }
1656}
1657
1658impl GeometryTrait for Polyline {
1659    type T = f64;
1660    type PointType<'b>
1661        = &'b Point
1662    where
1663        Self: 'b;
1664    type LineStringType<'b>
1665        = LineString<'b>
1666    where
1667        Self: 'b;
1668    type PolygonType<'b>
1669        = UnimplementedPolygon<Self::T>
1670    where
1671        Self: 'b;
1672    type MultiPointType<'b>
1673        = UnimplementedMultiPoint<Self::T>
1674    where
1675        Self: 'b;
1676    type MultiLineStringType<'b>
1677        = Self
1678    where
1679        Self: 'b;
1680    type MultiPolygonType<'b>
1681        = UnimplementedMultiPolygon<Self::T>
1682    where
1683        Self: 'b;
1684    type GeometryCollectionType<'b>
1685        = geo_traits::UnimplementedGeometryCollection<Self::T>
1686    where
1687        Self: 'b;
1688    type RectType<'b>
1689        = geo_traits::UnimplementedRect<f64>
1690    where
1691        Self: 'b;
1692    type LineType<'b>
1693        = geo_traits::UnimplementedLine<f64>
1694    where
1695        Self: 'b;
1696    type TriangleType<'b>
1697        = geo_traits::UnimplementedTriangle<f64>
1698    where
1699        Self: 'b;
1700
1701    fn dim(&self) -> geo_traits::Dimensions {
1702        geo_traits::Dimensions::Xy
1703    }
1704
1705    fn as_type(
1706        &self,
1707    ) -> geo_traits::GeometryType<
1708        '_,
1709        Self::PointType<'_>,
1710        Self::LineStringType<'_>,
1711        Self::PolygonType<'_>,
1712        Self::MultiPointType<'_>,
1713        Self::MultiLineStringType<'_>,
1714        Self::MultiPolygonType<'_>,
1715        Self::GeometryCollectionType<'_>,
1716        Self::RectType<'_>,
1717        Self::TriangleType<'_>,
1718        Self::LineType<'_>,
1719    > {
1720        geo_traits::GeometryType::MultiLineString(self)
1721    }
1722}
1723
1724impl GeometryTrait for PolylineM {
1725    type T = f64;
1726    type PointType<'b>
1727        = &'b PointM
1728    where
1729        Self: 'b;
1730    type LineStringType<'b>
1731        = LineStringM<'b>
1732    where
1733        Self: 'b;
1734    type PolygonType<'b>
1735        = UnimplementedPolygon<Self::T>
1736    where
1737        Self: 'b;
1738    type MultiPointType<'b>
1739        = UnimplementedMultiPoint<Self::T>
1740    where
1741        Self: 'b;
1742    type MultiLineStringType<'b>
1743        = Self
1744    where
1745        Self: 'b;
1746    type MultiPolygonType<'b>
1747        = UnimplementedMultiPolygon<Self::T>
1748    where
1749        Self: 'b;
1750    type GeometryCollectionType<'b>
1751        = geo_traits::UnimplementedGeometryCollection<Self::T>
1752    where
1753        Self: 'b;
1754    type RectType<'b>
1755        = geo_traits::UnimplementedRect<f64>
1756    where
1757        Self: 'b;
1758    type LineType<'b>
1759        = geo_traits::UnimplementedLine<f64>
1760    where
1761        Self: 'b;
1762    type TriangleType<'b>
1763        = geo_traits::UnimplementedTriangle<f64>
1764    where
1765        Self: 'b;
1766
1767    fn dim(&self) -> geo_traits::Dimensions {
1768        geo_traits::Dimensions::Xym
1769    }
1770
1771    fn as_type(
1772        &self,
1773    ) -> geo_traits::GeometryType<
1774        '_,
1775        Self::PointType<'_>,
1776        Self::LineStringType<'_>,
1777        Self::PolygonType<'_>,
1778        Self::MultiPointType<'_>,
1779        Self::MultiLineStringType<'_>,
1780        Self::MultiPolygonType<'_>,
1781        Self::GeometryCollectionType<'_>,
1782        Self::RectType<'_>,
1783        Self::TriangleType<'_>,
1784        Self::LineType<'_>,
1785    > {
1786        geo_traits::GeometryType::MultiLineString(self)
1787    }
1788}
1789
1790impl GeometryTrait for PolylineZ {
1791    type T = f64;
1792    type PointType<'b>
1793        = &'b PointZ
1794    where
1795        Self: 'b;
1796    type LineStringType<'b>
1797        = LineStringZ<'b>
1798    where
1799        Self: 'b;
1800    type PolygonType<'b>
1801        = UnimplementedPolygon<Self::T>
1802    where
1803        Self: 'b;
1804    type MultiPointType<'b>
1805        = UnimplementedMultiPoint<Self::T>
1806    where
1807        Self: 'b;
1808    type MultiLineStringType<'b>
1809        = Self
1810    where
1811        Self: 'b;
1812    type MultiPolygonType<'b>
1813        = UnimplementedMultiPolygon<Self::T>
1814    where
1815        Self: 'b;
1816    type GeometryCollectionType<'b>
1817        = geo_traits::UnimplementedGeometryCollection<Self::T>
1818    where
1819        Self: 'b;
1820    type RectType<'b>
1821        = geo_traits::UnimplementedRect<f64>
1822    where
1823        Self: 'b;
1824    type LineType<'b>
1825        = geo_traits::UnimplementedLine<f64>
1826    where
1827        Self: 'b;
1828    type TriangleType<'b>
1829        = geo_traits::UnimplementedTriangle<f64>
1830    where
1831        Self: 'b;
1832
1833    fn dim(&self) -> geo_traits::Dimensions {
1834        // Check the first point to check if it's XYZ or XYZM
1835        self.parts
1836            .first()
1837            .and_then(|line_string| line_string.first().map(CoordTrait::dim))
1838            .unwrap_or(geo_traits::Dimensions::Xyz)
1839    }
1840
1841    fn as_type(
1842        &self,
1843    ) -> geo_traits::GeometryType<
1844        '_,
1845        Self::PointType<'_>,
1846        Self::LineStringType<'_>,
1847        Self::PolygonType<'_>,
1848        Self::MultiPointType<'_>,
1849        Self::MultiLineStringType<'_>,
1850        Self::MultiPolygonType<'_>,
1851        Self::GeometryCollectionType<'_>,
1852        Self::RectType<'_>,
1853        Self::TriangleType<'_>,
1854        Self::LineType<'_>,
1855    > {
1856        geo_traits::GeometryType::MultiLineString(self)
1857    }
1858}
1859
1860impl GeometryTrait for MultiPolygon {
1861    type T = f64;
1862    type PointType<'b>
1863        = &'b Point
1864    where
1865        Self: 'b;
1866    type LineStringType<'b>
1867        = LineString<'b>
1868    where
1869        Self: 'b;
1870    type PolygonType<'b>
1871        = &'b Polygon
1872    where
1873        Self: 'b;
1874    type MultiPointType<'b>
1875        = UnimplementedMultiPoint<Self::T>
1876    where
1877        Self: 'b;
1878    type MultiLineStringType<'b>
1879        = UnimplementedMultiLineString<Self::T>
1880    where
1881        Self: 'b;
1882    type MultiPolygonType<'b>
1883        = Self
1884    where
1885        Self: 'b;
1886    type GeometryCollectionType<'b>
1887        = geo_traits::UnimplementedGeometryCollection<Self::T>
1888    where
1889        Self: 'b;
1890    type RectType<'b>
1891        = geo_traits::UnimplementedRect<f64>
1892    where
1893        Self: 'b;
1894    type LineType<'b>
1895        = geo_traits::UnimplementedLine<f64>
1896    where
1897        Self: 'b;
1898    type TriangleType<'b>
1899        = geo_traits::UnimplementedTriangle<f64>
1900    where
1901        Self: 'b;
1902
1903    fn dim(&self) -> geo_traits::Dimensions {
1904        geo_traits::Dimensions::Xy
1905    }
1906
1907    fn as_type(
1908        &self,
1909    ) -> geo_traits::GeometryType<
1910        '_,
1911        Self::PointType<'_>,
1912        Self::LineStringType<'_>,
1913        Self::PolygonType<'_>,
1914        Self::MultiPointType<'_>,
1915        Self::MultiLineStringType<'_>,
1916        Self::MultiPolygonType<'_>,
1917        Self::GeometryCollectionType<'_>,
1918        Self::RectType<'_>,
1919        Self::TriangleType<'_>,
1920        Self::LineType<'_>,
1921    > {
1922        geo_traits::GeometryType::MultiPolygon(self)
1923    }
1924}
1925
1926impl GeometryTrait for MultiPolygonM {
1927    type T = f64;
1928    type PointType<'b>
1929        = &'b PointM
1930    where
1931        Self: 'b;
1932    type LineStringType<'b>
1933        = LineStringM<'b>
1934    where
1935        Self: 'b;
1936    type PolygonType<'b>
1937        = &'b PolygonM
1938    where
1939        Self: 'b;
1940    type MultiPointType<'b>
1941        = UnimplementedMultiPoint<Self::T>
1942    where
1943        Self: 'b;
1944    type MultiLineStringType<'b>
1945        = UnimplementedMultiLineString<Self::T>
1946    where
1947        Self: 'b;
1948    type MultiPolygonType<'b>
1949        = Self
1950    where
1951        Self: 'b;
1952    type GeometryCollectionType<'b>
1953        = geo_traits::UnimplementedGeometryCollection<Self::T>
1954    where
1955        Self: 'b;
1956    type RectType<'b>
1957        = geo_traits::UnimplementedRect<f64>
1958    where
1959        Self: 'b;
1960    type LineType<'b>
1961        = geo_traits::UnimplementedLine<f64>
1962    where
1963        Self: 'b;
1964    type TriangleType<'b>
1965        = geo_traits::UnimplementedTriangle<f64>
1966    where
1967        Self: 'b;
1968
1969    fn dim(&self) -> geo_traits::Dimensions {
1970        geo_traits::Dimensions::Xym
1971    }
1972
1973    fn as_type(
1974        &self,
1975    ) -> geo_traits::GeometryType<
1976        '_,
1977        Self::PointType<'_>,
1978        Self::LineStringType<'_>,
1979        Self::PolygonType<'_>,
1980        Self::MultiPointType<'_>,
1981        Self::MultiLineStringType<'_>,
1982        Self::MultiPolygonType<'_>,
1983        Self::GeometryCollectionType<'_>,
1984        Self::RectType<'_>,
1985        Self::TriangleType<'_>,
1986        Self::LineType<'_>,
1987    > {
1988        geo_traits::GeometryType::MultiPolygon(self)
1989    }
1990}
1991
1992impl GeometryTrait for MultiPolygonZ {
1993    type T = f64;
1994    type PointType<'b>
1995        = &'b PointZ
1996    where
1997        Self: 'b;
1998    type LineStringType<'b>
1999        = LineStringZ<'b>
2000    where
2001        Self: 'b;
2002    type PolygonType<'b>
2003        = &'b PolygonZ
2004    where
2005        Self: 'b;
2006    type MultiPointType<'b>
2007        = UnimplementedMultiPoint<Self::T>
2008    where
2009        Self: 'b;
2010    type MultiLineStringType<'b>
2011        = UnimplementedMultiLineString<Self::T>
2012    where
2013        Self: 'b;
2014    type MultiPolygonType<'b>
2015        = Self
2016    where
2017        Self: 'b;
2018    type GeometryCollectionType<'b>
2019        = geo_traits::UnimplementedGeometryCollection<Self::T>
2020    where
2021        Self: 'b;
2022    type RectType<'b>
2023        = geo_traits::UnimplementedRect<f64>
2024    where
2025        Self: 'b;
2026    type LineType<'b>
2027        = geo_traits::UnimplementedLine<f64>
2028    where
2029        Self: 'b;
2030    type TriangleType<'b>
2031        = geo_traits::UnimplementedTriangle<f64>
2032    where
2033        Self: 'b;
2034
2035    fn dim(&self) -> geo_traits::Dimensions {
2036        // Check the first polygon to check if it's XYZ or XYZM
2037        self.0
2038            .first()
2039            .map(|polygon| polygon.dim())
2040            .unwrap_or(geo_traits::Dimensions::Xyz)
2041    }
2042
2043    fn as_type(
2044        &self,
2045    ) -> geo_traits::GeometryType<
2046        '_,
2047        Self::PointType<'_>,
2048        Self::LineStringType<'_>,
2049        Self::PolygonType<'_>,
2050        Self::MultiPointType<'_>,
2051        Self::MultiLineStringType<'_>,
2052        Self::MultiPolygonType<'_>,
2053        Self::GeometryCollectionType<'_>,
2054        Self::RectType<'_>,
2055        Self::TriangleType<'_>,
2056        Self::LineType<'_>,
2057    > {
2058        geo_traits::GeometryType::MultiPolygon(self)
2059    }
2060}