Merge pull request #2 from kjordahl/feature-operators

Implement set operators
This commit is contained in:
Kelsey Jordahl
2013-07-02 20:10:10 -07:00
2 changed files with 70 additions and 5 deletions
+44
View File
@@ -341,6 +341,50 @@ class GeoSeries(Series):
def project(self, *args, **kwargs):
raise NotImplementedError
#
# Implement standard operators for GeoSeries
#
def __contains__(self, other):
"""
Allow tests of the form "geom in s" to test whether a GeoSeries
contains a geometry.
Note: This is not the same as the geometric method "contains".
"""
if isinstance(other, BaseGeometry):
return np.any(self.equals(other))
else:
return False
def __xor__(self, other):
"""
The ^ operator implements symmetric_difference() as it does
for the builtin set type.
"""
return self.symmetric_difference(other)
def __or__(self, other):
"""
The | operator implements union() as it does
for the builtin set type.
"""
return self.union(other)
def __and__(self, other):
"""
The & operator implements intersection() as it does
for the builtin set type.
"""
return self.intersection(other)
def __sub__(self, other):
"""
The - operator implements difference() as it does
for the builtin set type.
"""
return self.difference(other)
#
# Implement pandas methods
#
+26 -5
View File
@@ -4,6 +4,15 @@ from shapely.geometry import Polygon, Point, LineString
from geopandas import GeoSeries
def geom_equals(this, that):
"""
Test for geometric equality, allowing all empty geometries to be considered equal
"""
empty = np.logical_and(this.is_empty, that.is_empty)
eq = this.equals(that)
return np.all(np.logical_or(eq, empty))
class TestSeries(unittest.TestCase):
def setUp(self):
@@ -22,6 +31,12 @@ class TestSeries(unittest.TestCase):
def test_area(self):
assert np.allclose(self.g1.area.values, np.array([0.5, 1.0]))
def test_in(self):
assert self.t1 in self.g1
assert self.sq in self.g1
assert self.t1 in self.a1
assert self.t2 in self.g3
def test_boundary(self):
l1 = LineString([(0, 0), (1, 0), (1, 1), (0, 0)])
l2 = LineString([(0, 0), (1, 0), (1, 1), (0, 1), (0, 0)])
@@ -89,31 +104,37 @@ class TestSeries(unittest.TestCase):
# TODO
pass
def test_intersection(self):
assert geom_equals(self.g1 & self.g2, self.t1)
def test_union_series(self):
u = self.g1.union(self.g2)
assert u[0].equals(self.sq)
assert u[1].equals(self.sq)
assert geom_equals(u, self.g1 | self.g2)
def test_union_polgon(self):
u = self.g1.union(self.t2)
assert u[0].equals(self.sq)
assert u[1].equals(self.sq)
def test_difference_series(self):
u = self.g1.difference(self.g2)
assert u[0].is_empty
assert u[1].equals(self.t2)
def test_symmetric_difference_series(self):
u = self.g3.symmetric_difference(self.g4)
assert u[0].equals(self.sq)
assert u[1].equals(self.sq)
assert geom_equals(u, self.g3 ^ self.g4)
def test_symmetric_difference_poly(self):
u = self.g3.symmetric_difference(self.t1)
assert u[0].is_empty
assert u[1].equals(self.sq)
def test_difference_series(self):
u = self.g1.difference(self.g2)
assert u[0].is_empty
assert u[1].equals(self.t2)
assert geom_equals(u, self.g1 - self.g2)
def test_difference_poly(self):
u = self.g1.difference(self.t2)
assert u[0].equals(self.t1)