Struct geo::algorithm::relate::IntersectionMatrix
source · pub struct IntersectionMatrix(/* private fields */);
Expand description
Models a Dimensionally Extended Nine-Intersection Model (DE-9IM) matrix.
DE-9IM matrix values (such as “212FF1FF2”) specify the topological relationship between two Geometries.
DE-9IM matrices are 3x3 matrices that represent the topological locations that occur in a geometry (Interior, Boundary, Exterior).
The indices are provided by the enum cases CoordPos::Inside, CoordPos::OnBoundary, CoordPos::Outside.
The matrix entries represent the Dimensions of each intersection.
For a description of the DE-9IM and the spatial predicates derived from it, see the following references:
- OGC 99-049 OpenGIS Simple Features Specification for SQL, Section 2.1.13
- OGC 06-103r4 OpenGIS Implementation Standard for Geographic information - Simple feature access - Part 1: Common architecture, Section 6.1.15 (which provides some further details on certain predicate specifications).
- Wikipedia article on DE-9IM
This implementation is heavily based on that from the JTS project.
Implementations§
source§impl IntersectionMatrix
impl IntersectionMatrix
pub fn empty() -> Self
sourcepub fn is_disjoint(&self) -> bool
pub fn is_disjoint(&self) -> bool
Returns true
if geometries a
and b
are disjoint: they have no point in common,
forming a set of disconnected geometries.
§Notes
- Matches
[FF*FF****]
- This predicate is anti-reflexive
sourcepub fn is_intersects(&self) -> bool
pub fn is_intersects(&self) -> bool
Tests if IntersectionMatrix::is_disjoint
returns false
.
Returns true
if the two geometries related by this matrix intersect: they have at least one point in common.
§Notes
- Matches any of
[T********], [*T*******], [***T*****], [****T****]
- This predicate is reflexive and symmetric
sourcepub fn is_within(&self) -> bool
pub fn is_within(&self) -> bool
Returns true
if the first geometry is within the second: a
lies in the interior of b
.
§Notes
- Also known as inside
- The mask
[T*F**F***
] occurs in the definition of bothIntersectionMatrix::is_within
andIntersectionMatrix::is_coveredby
; For most situations,IntersectionMatrix::is_coveredby
should be used in preference toIntersectionMatrix::is_within
- This predicate is reflexive and transitive
sourcepub fn is_contains(&self) -> bool
pub fn is_contains(&self) -> bool
Returns true
if geometry a
contains geometry b
.
§Notes
- Matches
[T*****FF*]
- This predicate is reflexive and transitive
sourcepub fn is_equal_topo(&self) -> bool
pub fn is_equal_topo(&self) -> bool
Returns true
if the first geometry is topologically equal to the second.
§Notes
- Matches
[T*F**FFF*]
- This predicate is reflexive, symmetric, and transitive
sourcepub fn is_coveredby(&self) -> bool
pub fn is_coveredby(&self) -> bool
Returns true if every point in Geometry a
lies inside (i.e. intersects the interior or boundary of) Geometry b
.
Equivalently, tests that no point of a
lies outside (in the exterior of) b
:
a
is covered byb
(extendsIntersectionMatrix::is_within
): geometrya
lies inb
. OR- At least one point of
a
lies inb
, and no point ofa
lies in the exterior ofb
OR - Every point of
a
is a point of (the interior or boundary of)b
returns true
if the first geometry is covered by the second.
use geo_types::{Polygon, polygon};
use geo::relate::Relate;
let poly1 = polygon![
(x: 125., y: 179.),
(x: 110., y: 150.),
(x: 160., y: 160.),
(x: 125., y: 179.),
];
let poly2 = polygon![
(x: 124., y: 182.),
(x: 106., y: 146.),
(x: 162., y: 159.),
(x: 124., y: 182.),
];
let intersection = poly1.relate(&poly2);
assert_eq!(intersection.is_coveredby(), true);
§Notes
- Matches any of
[T*F**F***], [*TF**F***], [**FT*F***], [**F*TF***]
- This predicate is reflexive and transitive
sourcepub fn is_covers(&self) -> bool
pub fn is_covers(&self) -> bool
Returns true
if every point in Geometry b
lies inside
(i.e. intersects the interior or boundary of) Geometry a
. Equivalently,
tests that no point of b
lies outside (in the exterior of) a
.
§Notes
- Unlike
IntersectionMatrix::is_contains
, it does not distinguish between points in the boundary and in the interior of geometries - For most situations,
IntersectionMatrix::is_covers
should be used in preference toIntersectionMatrix::is_contains
- Matches any of
[T*****FF*], [*T****FF*], [***T**FF*], [****T*FF*]
- This predicate is reflexive and transitive
sourcepub fn is_touches(&self) -> bool
pub fn is_touches(&self) -> bool
Returns true
if a
touches b
: they have at least one point in common, but their
interiors do not intersect.
§Notes
- Matches any of
[FT*******], [F**T*****], [F***T****]
- This predicate is symmetric
sourcepub fn is_crosses(&self) -> bool
pub fn is_crosses(&self) -> bool
Compares two geometry objects and returns true
if their intersection “spatially crosses”;
that is, the geometries have some, but not all interior points in common
use geo_types::{LineString, line_string, polygon};
use geo::relate::Relate;
let line_string: LineString = line_string![(x: 85.0, y: 194.0), (x: 162.0, y: 135.0)];
let poly = polygon![
(x: 125., y: 179.),
(x: 110., y: 150.),
(x: 160., y: 160.),
(x: 125., y: 179.),
];
let intersection = line_string.relate(&poly);
assert_eq!(intersection.is_crosses(), true);
§Notes
- If any of the following do not hold, the function will return
false
:- The intersection of the interiors of the geometries must be non-empty
- The intersection must have dimension less than the maximum dimension of the two input geometries (two polygons cannot cross)
- The intersection of the two geometries must not equal either geometry (two points cannot cross)
- Matches one of
[T*T******] (a < b)
,[T*****T**] (a > b)
,[0********] (dimensions == 1)
- This predicate is symmetric and irreflexive
sourcepub fn is_overlaps(&self) -> bool
pub fn is_overlaps(&self) -> bool
Returns true
if geometry a
and b
“spatially overlap”. Two geometries overlap if they have the
same dimension, their interiors intersect in that dimension, and each has at least one point
inside the other (or equivalently, neither one covers the other)
use geo_types::{Polygon, polygon};
use geo::relate::Relate;
let poly1 = polygon![
(x: 125., y: 179.),
(x: 110., y: 150.),
(x: 160., y: 160.),
(x: 125., y: 179.),
];
let poly2 = polygon![
(x: 126., y: 179.),
(x: 110., y: 150.),
(x: 161., y: 160.),
(x: 126., y: 179.),
];
let intersection = poly1.relate(&poly2);
assert_eq!(intersection.is_overlaps(), true);
§Notes
- Matches one of
[1*T***T**] (dimensions == 1)
,[T*T***T**] (dimensions == 0 OR 2)
- This predicate is symmetric
sourcepub fn get(&self, lhs: CoordPos, rhs: CoordPos) -> Dimensions
pub fn get(&self, lhs: CoordPos, rhs: CoordPos) -> Dimensions
Directly accesses this matrix
use geo_types::{LineString, Rect, line_string};
use geo::{coordinate_position::CoordPos, dimensions::Dimensions, relate::Relate};
let line_string: LineString = line_string![(x: 0.0, y: 0.0), (x: 10.0, y: 0.0), (x: 5.0, y: 5.0)];
let rect = Rect::new((0.0, 0.0), (5.0, 5.0));
let intersection = line_string.relate(&rect);
// The intersection of the two interiors is empty, because no part of the string is inside the rect
assert_eq!(intersection.get(CoordPos::Inside, CoordPos::Inside), Dimensions::Empty);
// The intersection of the line string's interior with the rect's boundary is one-dimensional, because part of the first line overlaps one of the rect's edges
assert_eq!(intersection.get(CoordPos::Inside, CoordPos::OnBoundary), Dimensions::OneDimensional);
// The intersection of the line string's interior with the rect's exterior is one-dimensional, because part of the string is outside the rect
assert_eq!(intersection.get(CoordPos::Inside, CoordPos::Outside), Dimensions::OneDimensional);
// The intersection of the line string's boundary with the rect's interior is empty, because neither of its end points are inside the rect
assert_eq!(intersection.get(CoordPos::OnBoundary, CoordPos::Inside), Dimensions::Empty);
// The intersection of the line string's boundary with the rect's boundary is zero-dimensional, because the string's start and end points are on the rect's edges
assert_eq!(intersection.get(CoordPos::OnBoundary, CoordPos::OnBoundary), Dimensions::ZeroDimensional);
// The intersection of the line string's boundary with the rect's exterior is empty, because neither of its end points are outside the rect
assert_eq!(intersection.get(CoordPos::OnBoundary, CoordPos::Outside), Dimensions::Empty);
// The intersection of the the line's exterior with the rect's interior is two-dimensional, because it's simply the rect's interior
assert_eq!(intersection.get(CoordPos::Outside, CoordPos::Inside), Dimensions::TwoDimensional);
// The intersection of the line's exterior with the rect's boundary is one-dimensional, because it's the rect's edges (minus where the string overlaps it)
assert_eq!(intersection.get(CoordPos::Outside, CoordPos::OnBoundary), Dimensions::OneDimensional);
// The intersection of the two exteriors is two-dimensional, because it's the whole plane around the two shapes
assert_eq!(intersection.get(CoordPos::Outside, CoordPos::Outside), Dimensions::TwoDimensional);
sourcepub fn matches(&self, spec: &str) -> Result<bool, InvalidInputError>
pub fn matches(&self, spec: &str) -> Result<bool, InvalidInputError>
Does the intersection matrix match the provided DE-9IM specification string?
A DE-9IM spec string must be 9 characters long, and each character must be one of the following:
- 0: matches a 0-dimensional (point) intersection
- 1: matches a 1-dimensional (line) intersection
- 2: matches a 2-dimensional (area) intersection
- f or F: matches only empty dimensions
- t or T: matches anything non-empty
- *: matches anything
use geo::algorithm::Relate;
use geo::geometry::Polygon;
use wkt::TryFromWkt;
let a = Polygon::<f64>::try_from_wkt_str("POLYGON((0 0,4 0,4 4,0 4,0 0))").expect("valid WKT");
let b = Polygon::<f64>::try_from_wkt_str("POLYGON((1 1,4 0,4 4,0 4,1 1))").expect("valid WKT");
let im = a.relate(&b);
assert!(im.matches("212F11FF2").expect("valid DE-9IM spec"));
assert!(im.matches("TTT***FF2").expect("valid DE-9IM spec"));
assert!(!im.matches("TTT***FFF").expect("valid DE-9IM spec"));
Trait Implementations§
source§impl Clone for IntersectionMatrix
impl Clone for IntersectionMatrix
source§fn clone(&self) -> IntersectionMatrix
fn clone(&self) -> IntersectionMatrix
1.0.0 · source§fn clone_from(&mut self, source: &Self)
fn clone_from(&mut self, source: &Self)
source
. Read moresource§impl Debug for IntersectionMatrix
impl Debug for IntersectionMatrix
source§impl FromStr for IntersectionMatrix
impl FromStr for IntersectionMatrix
Build an IntersectionMatrix based on a string specification.
use geo::algorithm::relate::IntersectionMatrix;
use std::str::FromStr;
let intersection_matrix = IntersectionMatrix::from_str("212101212").expect("valid DE-9IM specification");
assert!(intersection_matrix.is_intersects());
assert!(!intersection_matrix.is_contains());
source§impl PartialEq for IntersectionMatrix
impl PartialEq for IntersectionMatrix
source§fn eq(&self, other: &IntersectionMatrix) -> bool
fn eq(&self, other: &IntersectionMatrix) -> bool
self
and other
values to be equal, and is used
by ==
.