XML/KML - 如何在 bash 脚本中测试一个多边形 'touches' 另一个多边形

XML/KML - How to test if a polygon 'touches' another polygon in a bash script

我正在使用 Google 我的地图在一层上绘制郊区(作为多边形),然后在第二层上绘制存在于其内部和周围的所有(农村)属性(也作为多边形)那个郊区。多边形使用地理坐标来定义点。例如(略有编辑):

        <Polygon>
          <outerBoundaryIs>
            <LinearRing>
              <tessellate>1</tessellate>
              <coordinates>
                150.523000,-34.720000,0
                150.524000,-34.719000,0
                150.524000,-34.719000,0
                150.524000,-34.719000,0
                150.523000,-34.719000,0
                150.523000,-34.720000,0
                150.523000,-34.720000,0
              </coordinates>
            </LinearRing>
          </outerBoundaryIs>
        </Polygon>

然后我使用 bash 脚本修改 XML/KML 以满足我的要求。

我希望有人有灵丹妙药,可以通过命令行指定一个 XML 文件和两个多边形的 XPATH(在 XML 文件中)和让它告诉我这两个多边形是否相交 - 例如:

check_polygons "/path/to/XML" "//_:xpath/to/polygon1" "//_:xpath/to/polygon2"

它以某种方式(文本或退出状态)告诉我这两个多边形是否在任何点相交。

非常感谢任何帮助。

感谢 Paul Hodges 鼓励我,让我努力想出解决方案。

这非常适合我使用 Google 我的地图创建两层地图的情况。第一层名为 'Locality',是一个绘制郊区的多边形。第二层名为 'Property',包含映射 属性 边界的多个多边形。

下面的脚本有 2 个或 3 个参数。第一个(可选)参数是 XML 命名空间(默认为 http://www.opengis.net/kml/2.2),第二个参数是 'Property' 图层上的地标名称,最后一个参数是 KML 文件名。该脚本检查两个多边形是否相交。如果他们这样做,它会打印 True 并且 return 代码为 0(零)。如果它们不相交,它会打印 False 并且 return 代码为 1。return 代码为 2 表示在 XML 中找不到 XPath文件或存在使用错误。

#!/usr/bin/python

from lxml import etree
from shapely.geometry import Polygon
import sys


def getPoly(XmlFile, XmlNS, XPath):
    tree = etree.parse(XmlFile)
    root = tree.getroot()
    XmlNamespace = {"NS": XmlNS}
    xmlList = root.xpath(XPath, namespaces=XmlNamespace)
    if not xmlList:
        return(False)
    polyCoordList = xmlList[0].text.replace(' ', '')
    coordinates = []
    for point_text in polyCoordList.split():
      floats = point_text.split(",")
      coordinates.append((float(floats[0]), float(floats[1])))
    return(Polygon(coordinates))



if __name__ == "__main__":
    XmlNS = "http://www.opengis.net/kml/2.2"
    if len(sys.argv) == 4:
        XmlNS = sys.argv[1]
        XmlPlacemarkName = sys.argv[2]
        XmlFile = sys.argv[3]
    elif len(sys.argv) == 3:
        XmlPlacemarkName = sys.argv[1]
        XmlFile = sys.argv[2]
    else:
        print("Usage: %s [NameSpace] PlacemarkName KmlFile" % (sys.argv[0]))
        print("The default namespace is %s" % XmlNS)
        exit(2)


    XPath = "./NS:Document/NS:Folder[contains(., 'Locality')]/NS:Placemark/NS:Polygon/NS:outerBoundaryIs/NS:LinearRing/NS:coordinates"
    LocalityPoly = getPoly(XmlFile, XmlNS, XPath)
    if LocalityPoly == False:
        print("Invalid XPath - %s" % XPath)
        exit(2)
    XPath = "./NS:Document/NS:Folder[contains(., 'Property')]/NS:Placemark[contains(., '%s')]/NS:Polygon/NS:outerBoundaryIs/NS:LinearRing/NS:coordinates" % XmlPlacemarkName
    PlacemarkPoly = getPoly(XmlFile, XmlNS, XPath)
    if PlacemarkPoly == False:
        XPath = "./NS:Document/NS:Folder[contains(., 'Property')]/NS:Placemark[contains(., '%s')]/NS:MultiGeometry/NS:Polygon/NS:outerBoundaryIs/NS:LinearRing/NS:coordinates" % XmlPlacemarkName
        PlacemarkPoly = getPoly(XmlFile, XmlNS, XPath)
        if PlacemarkPoly == False:
            print("Invalid XPath - %s" % XPath)
            exit(2)
    result = LocalityPoly.intersects(PlacemarkPoly)
    print(result)
    exit(not result)

希望对其他人有所帮助。