簡體   English   中英

使用JTS庫檢測LineString / MultiLineString是否在多邊形內部或與之相交

[英]Detect if a LineString / MultiLineString is inside a Polygon or if it intersects it using JTS library

描述

因此,基本上我想知道的是MultiPolygon是否包含LineString (或MultiLineString )或與之相交。

我不確定是否會影響它,但實際情況是我有一個代表遠足徑的LineString ,我需要知道該徑穿過哪個世界區域(這就是我的MultiPolygon ) 。 或者,如果它在我的世界區域之一之內,我需要知道哪個區域包含該LineString

我的問題

我在這里的問題是我得到了誤報 如果我對Point進行相同的檢查(以查看它是否包含在MultiPolygon ),而不是LineString ,則可以正常工作。

完成我的目標的步驟:

  1. 將我的LineString從EPSG 3857格式處理為EPSG 4326格式(使用此公式將坐標從EPSG 3857轉換為4326 DotSpatial ),因為我收到的LineString是EPSG 3857格式。
  2. 閱讀我的Geometries (使用GsonJtsAdapter ,因為它們是GeoJson格式,具體來說是MultiPolygon )。 這一點應該不是問題,因為我使用它來檢測Point是否在其他地方的Polygon內部,並且可以正常工作。
  3. 檢查我的LineString是否相交或包含在任何MultiPolygon並注冊此MultiPolygon的所有ID。

我的代碼:

1,將我的LineString從EPSG 3857轉換為EPSG 4326:

private fun reprojectFromEpsg3857ToEpsg4326(geometry: Geometry): Geometry
{
    val e = 2.7182818284
    val X = 20037508.34

    if (geometry is LineString) {
        for (i in 0 until geometry.numPoints) {
            val coordinate = geometry.getCoordinateN(i)
            geometry.getCoordinateN(i).x = (coordinate.x * 180) / X
            geometry.getCoordinateN(i).y = coordinate.y / (X / 180)
            geometry.getCoordinateN(i).y = ((Math.atan(Math.pow(e, ((PI / 180) * geometry.getCoordinateN(i).y)))) / (PI / 360)) - 90
        }
    } else if (geometry is MultiLineString) {
        try {
            for (i in 0 until geometry.numGeometries) {
                for (j in 0 until geometry.getGeometryN(i).coordinates.size) {
                    val coordinate = geometry.getGeometryN(i).coordinates[i]
                    geometry.getGeometryN(i).coordinates[i].x = (coordinate.x * 180) / X
                    geometry.getGeometryN(i).coordinates[i].y = coordinate.y / (X / 180)
                    geometry.getGeometryN(i).coordinates[i].y = ((Math.atan(Math.pow(e,((PI / 180) * geometry.getGeometryN(i).coordinates[i].y)))) / (PI / 360)) - 90
                }
            }
        } catch (e: ArrayIndexOutOfBoundsException) {

        }
    }

    return geometry
}

2.使用Gson和Jts適配器閱讀我的Geometries

private fun getGeometries(gson: Gson): HashMap<Long, Geometry>
{
    val geoJsonGeometries = HashMap<Long, Geometry>()
    val geometriesFolder = File("geometries-folder")

    geometriesFolder.listFiles(getFilenameFilter("geojson")).forEach {
        val reader = FileReader(it)
        var geometry = gson.fromJson(reader, Geometry::class.java)

        if (geometry.geometryType == "GeometryCollection") {
            geometry = geometry.getGeometryN(0)
        }

        val geometryId = java.lang.Long.parseLong(it.name.replace(".geojson", ""))
        geoJsonGeometries[geometryId] = geometry
    }

    return geoJsonGeometries
}

3.執行檢查以查看哪些MultiPolygon與我的LineString相關(通過包含或通過相交):

val geometryIds = ArrayList<Long>()
geometries.forEach { geometryId, mapBoundaries ->
    if (routeAsLineString.intersects(mapBoundaries) || mapBoundaries.contains(routeAsLineString)) {
        geometryIds.add(geometryId)
    }
}

任何幫助將非常感激!

好吧,我非常錯誤地將MultiLineString從EPSG 3857格式轉換為EPSG 4326格式。 基本上,我不是在轉換MultiLineString ,只是在轉換第一個坐標。 但是, MultiLineString有許多Geometry對象,每個對象都有許多坐標。

因此,步驟2和3是正確的。

原始轉換為:

for (i in 0 until geometry.numGeometries) {
    for (j in 0 until geometry.getGeometryN(i).coordinates.size) {
        val coordinate = geometry.getGeometryN(i).coordinates[i]
        geometry.getGeometryN(i).coordinates[i].x = (coordinate.x * 180) / X
        geometry.getGeometryN(i).coordinates[i].y = coordinate.y / (X / 180)
        geometry.getGeometryN(i).coordinates[i].y = ((Math.atan(Math.pow(e,((PI / 180) * geometry.getGeometryN(i).coordinates[i].y)))) / (PI / 360)) - 90
    }
}

但應該是:

for (i in 0 until geometry.numGeometries) {
    for (j in 0 until geometry.getGeometryN(i).coordinates.size) {
        val coordinate = geometry.getGeometryN(i).coordinates[j]
        geometry.getGeometryN(i).coordinates[j].x = (coordinate.x * 180) / X
        geometry.getGeometryN(i).coordinates[j].y = coordinate.y / (X / 180)
        geometry.getGeometryN(i).coordinates[j].y = ((Math.atan(Math.pow(e,((PI / 180) * geometry.getGeometryN(i).coordinates[j].y)))) / (PI / 360)) - 90
    }
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM