จุด (ของการดึงแสง) ภายในรูปหลายเหลี่ยมโดยใช้ ogr และ Python


10

ขณะนี้ฉันกำลังทำงานในโครงการที่ฉันต้องการสร้างเครือข่ายทอพอโลยีจากคุณสมบัติทางเรขาคณิตที่ฉันพบในรูปร่างไฟล์ จนถึงตอนนี้การใช้โครงการโอเพ่นซอร์สของ Ben Reillyฉันได้ทำการแปลง linestrings เป็น edge networkx รวมถึงการตรวจสอบคุณสมบัติปิด (linestrings อื่นพูด) และเพิ่มไปยังจุดที่ใกล้ที่สุด

แต่มันก็ใช้ได้สำหรับไฟล์รูปร่างเดียว อย่างไรก็ตามตอนนี้ฉันต้องเชื่อมต่อฟีเจอร์ต่าง ๆ จากรูปร่างที่แตกต่างกันเข้ากับกราฟ networkx ขนาดใหญ่ ตัวอย่างเช่นถ้าจุดอยู่ภายในรูปหลายเหลี่ยมฉันจะเชื่อมต่อมัน (โดยเชื่อมต่อฉันหมายถึงเพิ่มขอบเครือข่าย - add_edge (g.GetPoint (1), g.GetPoint (2)) กับจุดในรูปร่างไฟล์ถัดไปที่ ยังอยู่ในรูปหลายเหลี่ยมที่ใช้แอตทริบิวต์ที่คล้ายกัน (พูด ID) โปรดทราบว่ารูปหลายเหลี่ยมในส่วนต่าง ๆ จะใช้รหัสเดียวกันเท่านั้นและไม่ใช่พิกัดจุดที่อยู่ภายในรูปหลายเหลี่ยมนั้นไม่ได้ใช้พิกัดเดียวกัน

วิธีแก้ไขปัญหานี้ของฉันคือการระบุจุดที่อยู่ในรูปหลายเหลี่ยมเก็บไว้ค้นหาจุดใน shapefile ถัดไปที่อยู่ในรูปหลายเหลี่ยมที่มี id เดียวกันและเพิ่ม networkx edge ระหว่างพวกเขา

จะหาได้อย่างไรว่าจุดนั้นอยู่ในรูปหลายเหลี่ยมหรือไม่? มีอัลกอริทึมที่รู้จักกันดี: อัลกอริทึมRayCastingที่ทำเช่นนั้น นี่คือจุดที่ฉันติดอยู่จริงเพราะเพื่อที่จะใช้อัลกอริทึมที่ฉันต้องการพิกัดของรูปหลายเหลี่ยมและไม่ทราบวิธีการเข้าถึงพวกเขาในขณะนี้แม้หลังจาก skimming ผ่านเอกสารของเรขาคณิตของ OGR ดังนั้นคำถามที่ฉันถามคือการเข้าถึงจุดรูปหลายเหลี่ยมหรือพิกัดหรือมีวิธีที่ง่ายกว่าในการตรวจสอบว่าจุดตกอยู่ในรูปหลายเหลี่ยม? การใช้ python กับ osgeo.ogr library ฉันเขียนโค้ดต่อไปนี้:

 if g.GetGeometryType() == 3: #polygon
                c = g.GetDimension()
                x = g.GetPointCount()
                y = g.GetY()
                z = g.GetZ()

ดูภาพเพื่อให้เข้าใจปัญหาของฉันได้ดีขึ้น ข้อความแสดงแทน

[แก้ไข] จนถึงตอนนี้ฉันพยายามเก็บวัตถุรูปหลายเหลี่ยมทั้งหมดในรายการที่ฉันจะเปรียบเทียบการเปล่งแสงแรกและจุดสุดท้าย แต่ตัวอย่างของเปาโลนั้นเกี่ยวข้องกับการใช้การอ้างอิงจุดวัตถุและการอ้างอิงวัตถุรูปหลายเหลี่ยมซึ่งจะไม่ทำงานกับการอ้างอิงวัตถุเส้นเนื่องจากไม่ใช่เส้นทั้งหมดอยู่ในรูปหลายเหลี่ยม แต่เป็นจุดแรกหรือจุดสุดท้ายของการส่องสว่างของมัน

[EDIT3] การสร้างวัตถุเรขาคณิตจุดใหม่จากพิกัดของจุดแรกและจุดสุดท้ายของการส่องแสงจากนั้นใช้การเปรียบเทียบนั้นกับวัตถุรูปหลายเหลี่ยมเรขาคณิตที่บันทึกในรายการดูเหมือนว่าจะทำงานได้ดี:

for findex in xrange(lyr.GetFeatureCount()):
    f = lyr.GetFeature(findex)
    flddata = getfieldinfo(lyr,f,fields)
    g = f.geometry()
    if g.GetGeometryType() == 2:
        for j in xrange(g.GetPointCount()):
            if j == 0 or j == g.GetPointCount():
                point = ogr.Geometry(ogr.wkbPoint)
                point.AddPoint(g.Getx(j),g.GetY(j))
                if point.Within(Network.polygons[x][0].GetGeometryRef()):
    print g.GetPoint(j)

ขอบคุณPaoloและChrisสำหรับคำแนะนำ

คำตอบ:


11

หุ่นดีเท่ห์และสง่างาม แต่ทำไมไม่ลองใช้ ogr กับโอเปอเรเตอร์อวกาศ (ในคลาส OGRGeometry)

รหัสตัวอย่าง:

from osgeo import ogr
driver = ogr.GetDriverByName('ESRI Shapefile')
polyshp = driver.Open('/home/pcorti/data/shapefile/multipoly.shp')
polylyr = polyshp.GetLayer(0)
pointshp = driver.Open('/home/pcorti/data/shapefile/point.shp')
pointlyr = pointshp.GetLayer(0)
point = pointlyr.GetNextFeature()
polygon = polylyr.GetNextFeature()
point_geom = point.GetGeometryRef()
polygon_geom = polygon.GetGeometryRef()
print point_geom.Within(polygon_geom)

โปรดทราบว่าคุณต้องรวบรวม GDAL ด้วยการสนับสนุน GEOS


grzie Paolo แต่สิ่งที่ฉันต้องการจริงๆคือไม่เปรียบเทียบการอ้างอิงวัตถุของจุดกับรูปหลายเหลี่ยม แต่เป็นจุดสุดท้ายและจุดแรกของการส่องสว่างซึ่งปัจจุบันฉันเข้าถึงด้วย GetPoint ฉันไม่สังเกตเห็น GetPointRef ฉันจะนำไปใช้อย่างไร
user39901230

1
linestring เป็นคอลเลคชั่นรูปทรงเรขาคณิตที่สามารถทำซ้ำได้ของจุด (จุดสุดยอด) คุณสามารถเข้าถึงจุดแรกและจุดสุดท้ายได้อย่างง่ายดาย
capooti

ฉันได้พยายามจัดเก็บวัตถุรูปหลายเหลี่ยมในรายการซึ่งฉันจะใช้ในการตรวจสอบกับจุดแรกและจุดสุดท้ายของ linestring ในภายหลัง แต่ไม่มีจุดจะมีการเพิ่มรายการของจุดภายในรูปหลายเหลี่ยมด้วยเหตุผลบางอย่างที่: ได้ดูที่นี่: codepad.org/Cm2BV5mp
user39901230

8

ฉันไม่คุ้นเคยกับ networkx แต่ถ้าฉันเข้าใจคำถามของคุณถูกต้องคุณสามารถใช้shapelyและ OGR lib เพื่อค้นหาจุดในรูปหลายเหลี่ยมจาก shapefile นี่คือตัวอย่างหนึ่งสำหรับการค้นหาว่าจุดใดจุดหนึ่ง (2000,1200) ล้มเหลวด้วยรูปหลายเหลี่ยมใด ๆ จากหนึ่งรูปร่างไฟล์ สำหรับผลลัพธ์มันพิมพ์พิกัดของรูปหลายเหลี่ยมนั้น

from shapely.geometry import Point, Polygon
from shapely.wkb import loads
from osgeo import ogr

file1 = ogr.Open("d:\\fileWithData.shp")
layer1 = file1.GetLayerByName("fileWithData")

point1 = Point(2000,1200)

polygon1 = layer1.GetNextFeature()

while polygon1 is not None:
    geomPolygon = loads(polygon1.GetGeometryRef().ExportToWkb())
    if geomPolygon.contains(point1):
        xList,yList = geomPolygon.exterior.xy
        print xList
        print yList
    polygon1 = layer1.GetNextFeature()

ฉันหวังว่ามันจะช่วย

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.