谓词,用来描述或判定客体性质、特征或者客体之间关系的词项。根据《现代汉语》的定义,汉语的体词包括名词,数词,量词;汉语的谓词包括动词和形容词。
from shapely.geometry import Point
Point(0, 0).has_z
Point(0, 0, 0).has_z
True
object.is_ccw
: 如果坐标是逆时针的,返回为真
(用正面标记的面积来框定区域)。这种方法仅适用于线性对象。
LinearRing([(1,0), (1,1), (0,0)]).is_ccw
非预期方向的环可以像这样反转:
from shapely.geometry import LinearRing
ring = LinearRing([(0,0), (1,1), (1,0)])
ring
ring.is_ccw
False
for cord in ring.coords:
print(cord)
(0.0, 0.0) (1.0, 1.0) (1.0, 0.0) (0.0, 0.0)
以下通过坐标顺序反转来构建新对象:
ring2 = LinearRing(list(ring.coords)[::-1])
ring2
ring2.is_ccw
True
object.is_empty
:
如果要素的内部与边界(在点集方面)和空集相配合,则返回为真。
from shapely.geometry import Point
Point().is_empty
Point(0, 0).is_empty
False
注意:
有operator
模块的attrgetter()
函数的帮助,一元谓词例如
is_empty
能够轻松地用作 filter()
或者itertools.ifilter()
内建的谓词。
from operator import attrgetter
empties = filter(attrgetter('is_empty'), [Point(), Point(0, 0)])
# len(empties)
object.is_ring
: 如果要素被闭合了,则返回为真。
一个关闭的要素的边界算是空集。
from shapely.geometry import LineString
LineString([(0, 0), (1, 1), (1, -1)]).is_ring
False
from shapely.geometry import LinearRing
LinearRing([(0, 0), (1, 1), (1, -1)]).is_ring
True
这属性适用于线(LineString)和线环(LinearRing)实例, 但是对于其它是毫无意义的。
object.is_simple
: 如果要素不是自相交的,则返回为真。
from shapely.geometry import LineString
LineString([(0, 0), (1, 1), (1, -1), (0, 1)]).is_simple
False
Shapely完全支持线环(LineStrings)的操作。
object.is_valid
: 如果一个要素是有效的,返回真。
一个有效的线环不能跨越它本身或者在一个单点接触。 一个有效的多边形可能拥有任何重叠的外部环或内部环。 一个有效的多元多边形可能不会搜集任何重叠的多边形。 基于无效要素进行的操作可能会失败。
from shapely.geometry import MultiPolygon
MultiPolygon([Point(0, 0).buffer(2.0), Point(1, 1).buffer(2.0)]).is_valid
False
以上2点接近,缓冲区操作产生的多边形将会重叠。(在下一节解释)
注意:
is_valid
谓词可以用来写一个验证修饰,
可以确保唯一有效的对象从构造函数中返回。
二元谓词
在Shapely中,标准的二元谓词通过Python的实现方法。这些谓词评估拓扑与集合论之间的关系。 在少数情况下,结果可能不是人们从不同假设中预期的那样。
所有二元谓词(方法)将另一个几何对象作为参数,且返回为真或为假。
object.almost_equals( other[, decimal=6])
如果对象的点在指定位精度上约等于另外对象的所有点, 则返回为真。
object.contains(other)
如果对象的内部包含另外一个对象的边界和内部, 并且两个对象的边界一点儿也不接触,则返回为真。
这种谓词适用于所有类型,并且逆于 a.contains(b) == b.within(a)的表达,常常被评定为真。
from shapely.geometry import Point, LineString
coords = [(0, 0), (1, 1)]
LineString(coords).contains(Point(0.5, 0.5))
True
from shapely.geometry import LineString
Point(0.5, 0.5).within(LineString(coords))
True
线的端点是边界的一部分, 因此不包含。例如:
LineString(coords).contains(Point(1.0, 1.0))
False
注意:
二元谓词可以直接用作filter()
或 itertools.ifilter()
的谓词。例如:
line = LineString(coords)
contained = filter(line.contains, [Point(), Point(0.5, 0.5)])
# len(contained)
object.crosses(other)
如果对象的内部与另外对象的内部相交但并不包含它,并且相交的维数少于它本身或另一个维数,则返回为真。
LineString(coords).crosses(LineString([(0, 1), (1, 0)]))
True
一条线不跨越它包含的点。
LineString(coords).crosses(Point(0.5, 0.5))
False
object.disjoint(other)
如果对象的边界和内部与其它对象一点儿也不相交,则返回为真。
Point(0, 0).disjoint(Point(1, 1))
True
这种谓词适用于所有类型并且逆于 intersects()
.
object.equals(other)
如果对象的集合论的边界、内部和外部与其它重合,则返回为真。
传递给对象构造的是这些集合, 并且决定它们,但是不是这些集的全部。 这对新用户来说是一个潜在的“疑难杂症”。 比如等值线,可以不这样被构造。
from shapely.geometry import LineString
a = LineString([(0, 0), (1, 1)])
b = LineString([(0, 0), (0.5, 0.5), (1, 1)])
c = LineString([(0, 0), (0, 0), (1, 1)])
a.equals(b)
True
b.equals(c)
True
这个谓词不应该被误认为是Python的==或者是构造。
object.intersects(other)
如果对象的边界和内部与其它的以任何形式相交,则返回真。
这个谓词不同于 contains()
、crosses()
、
equals()
、touches()
和within()
。
object.touches( other)
如果对象的边界仅仅与另一个对象的边界相交,并且不与另一个的任何部分相交,则返回为真。
叠置要素不是touch
, 另一个潜在的“疑难杂症”。
例如,下面的线在(1,1)相接触,但是并不重叠。
a = LineString([(0, 0), (1, 1)])
b = LineString([(1, 1), (2, 2)])
a.touches(b)
True
object.within(other)
如果对象的边界和内部仅仅与另一个内部(不是边界或者外部)相交,则返回为真。
这适用于所有的类型并且逆于 contains()
.
用于sorted()的关键词, within() 使它很容易在空间上进行分类。 比方说,我们有4种定型的要素: 一个被一个多边形包含的点,这个多边形被另一个多边形包含 和一个不被其它点包含的点。
from shapely.geometry import Point
from shapely.geometry import Polygon
a = Point(2, 2)
b = Polygon([[1, 1], [1, 3], [3, 3], [3, 1]])
c = Polygon([[0, 0], [0, 4], [4, 4], [4, 0]])
d = Point(-1, -1)
和列表中收集到的副本
features = [c, a, d, b, c]
列表中,我们更喜欢按照(d, c, c, b, a)的反向遏制秩序。 正如在Python中解释的那样, Sorting HowTo, 我们可以定义一个运行在每一个列表上的关键要素, 返回一个值用于比较。我们的关键要素将是一个封装类 用Shapely的二进制谓词实施。
二进制 within() 谓词。
# from shapely.geometry import asShape
class Within(object):
def __init__(self, o):
self.o = o
def __lt__(self, other):
return self.o.within(other.o)
正如howto所说的,小于比较的在排序中常被使用。 那正是我们空间排序中我们所依靠的东西, within() 和我们反向使用within() contains(). 而不是用contains()的原因。 在要素d和c上试验, 我们看到它工作了。
d > c
Within(d) > Within(c)
False
它对列表上的要素同样有效,并产生我们想要的顺序。
# features = [a,b,c,d]
# sorted(features, key=Within, reverse=True)
[d, c, c, b, a] == sorted(features, key=Within, reverse=True)
True