QGISを使用して、90%を超える別のベクターポリゴンレイヤーと重複しているポリゴンをプログラムで検索していますか


9

レイヤーの例

私はpythonを使用して、別のベクトルと> 90%重複している1つのベクトル内のポリゴンを抽出する方法を理解しようとしています。次に、これらのポリゴンのみを表示するベクター/マップが必要です。サンプル画像は私のレイヤーを示しています。90%を超える赤のすべての灰色のポリゴンが必要です。

私はこれをすべてpython(または同様に自動化された方法)で行う必要があります。同じ方法で処理するマップが1000個以下あります。


オーバーレイ「ユニオン」(基本についてはinfogeoblog.wordpress.com/2013/01/08/geo-processing-in-qgisを参照)を実行し、元のポリゴンごとに「in」統計と「out」統計を計算しますgis.stackexchange.com/questions/43037/...オーバーレイパーセントを決定するために...ヒント:あなたは面積計測持っている必要がありますgis.stackexchange.com/questions/23355/...
マイケル・スティムソン

ヒントをありがとう。それは私が今試みていたのと同じアプローチです。私は、Pythonコンソールを介して簡単にユニオンを実行できます。すでにエリア属性値に追加されています。わからない次のステップです。> 90%のポリゴンを識別/選択/クリップできるように、Pythonを使用して「イン」および「アウト」統計を計算するにはどうすればよいですか?
dnormous

Pythonがなくても可能だと思います。絶対にpythonが必要ですか、それとも仮想レイヤーのソリューションが適していますか?
Pierma

「イン」領域には両方のポリゴンの属性があり、「アウト」領域には1つのポリゴンセットの属性しかありません。エリア統計の両方のセットを取得し、元のポリゴンに結合して、「イン」、「アウト」、およびカバレッジのフィールドを追加し、エリアの合計から「イン」および「アウト」の値を計算してから、「イン」をパーセントを計算するための元の領域(または 'in' + 'out')。
Michael Stimson、2016年

1
Pierma-ポリゴンを見つけるための自動化された方法が必要なだけです。
'25年

回答:


3

次のコードはQGISのPythonコンソールで動作します。これにより、90%を超えるポリゴンが赤い領域でオーバーラップするメモリレイヤーが生成されます。

mapcanvas = iface.mapCanvas()

layers = mapcanvas.layers()

#for polygon_intersects
feats_lyr1 = [ feat for feat in layers[0].getFeatures() ]

#for xwRcl
feats_lyr2 = [ feat for feat in layers[1].getFeatures() ]

selected_feats = []

for i, feat1 in enumerate(feats_lyr1):
    area1 = 0
    area2 = 0
    for j, feat2 in enumerate(feats_lyr2):
        if feat1.geometry().intersects(feat2.geometry()):
            area = feat1.geometry().intersection(feat2.geometry()).area()
            print i, j, area, feat2.attribute('class')
            if feat2.attribute('class') == 1:
                area1 += area
            else:
                area2 += area
    crit = area1/(area1 + area2)
    print crit
    if crit > 0.9:
        selected_feats.append(feat1)

epsg = layers[0].crs().postgisSrid()

uri = "Polygon?crs=epsg:" + str(epsg) + "&field=id:integer""&index=yes"

mem_layer = QgsVectorLayer(uri,
                           "mem_layer",
                           "memory")

prov = mem_layer.dataProvider()

for i, feat in enumerate(selected_feats):
    feat.setAttributes([i])

prov.addFeatures(selected_feats)

QgsMapLayerRegistry.instance().addMapLayer(mem_layer)

次の2つのベクターレイヤーを使用してコードを試してみました。

ここに画像の説明を入力してください

結果を確証するために、QGISのPythonコンソールでコードを実行した後、インデックスが印刷されたI、関与する機能、交差領域内のフィールドの属性のJ polygons_intersects(灰色の領域のための赤色領域1及び2)と重複する基準。

0 0 9454207.56892 1
0 1 17429206.7906 2
0 2 10326705.2376 2
0 4 40775341.6814 1
0 5 26342803.0964 2
0 7 11875753.3216 2
0.432253120382
1 6 1198411.02558 2
1 7 1545489.96614 2
1 10 27511427.9909 1
0.90930850584
2 7 750262.940888 2
2 8 12012343.5859 1
0.941213972294
3 6 23321277.5158 2
0.0

作成されたメモリレイヤー(緑のフィーチャ)は、次の画像で確認できます。予想通りでした。

ここに画像の説明を入力してください


5

ここでは、Pythonを必要としないソリューションです。

次のようなクエリで新しい仮想レイヤーを追加します。

WITH r AS (
SELECT 
    Basins800.rowid AS idGray, 
    area(Basins800.geometry) AS areaGray, 
    area(Intersection(Basins800.geometry, Severity.geometry)) AS aeraInter, 
    Basins800.geometry AS geomGray 
  FROM Basins800, Severity
)

SELECT *, areaInterSum/areaGray  AS overlap , geomGray 
    FROM (
        SELECT 
           idGray, 
           areaGray, 
           sum(areaInter) AS areaInterSum, 
           geomGray 
        FROM r 
        GROUP BY idGray) 
     WHERE areaInterSum/areaGray > 0.9

と:

  • 灰色のポリゴンでフィルターしたいレイヤーとしてのBasins800

  • 重大度:赤いレイヤーが重なっています。

結果として、90%を超える灰色のすべての多角形だけが赤いポリゴンで重なり合った新しいレイヤーができ、新しいフィールドには重なり率が含まれます。

ここに画像の説明を入力してください

これがうまくいくことを願っています。必要に応じて、クエリの詳細を追加できます。

注:データには非常に小さなポリゴンが含まれています(ラスター処理から取得され、ラスターピクセルに対応しています(図では4つのポリゴンが表示されていますが、他に25個の小さなポリゴンがあります)。これにより、クエリの実行が非常に遅くなります(Intersection関数2つのレイヤから2つのフィーチャごとに1つのフィーチャを生成します)。


「仮想レイヤーの作成」ボタンを使用してクエリを実行すると、エラーが発生します。"CREATE TEMP VIEWのクエリ実行エラー_tview AS WITH r AS(" ....残りのコード......に続く: "1-near" WITH ":構文エラー"私はQGISを初めて使用しました。この仮想レイヤーをプログラムで作成しますか?ご協力ありがとうございます!
dnormous

シェープファイルをダウンロードするためのリンクは次のとおりです。リンク
dnormous

申し訳ありませんが、灰色と灰色の間の悪いコピーです(私の近くの英語では申し訳ありません)。クエリを編集しました。これで動作するはずです。なぜレイヤーをプログラマティックに作成したいのですか?仮想レイヤーの利点は、非破壊的であり、データ(灰色または赤いポリゴン)を編集すると、仮想レイヤーが自動的に更新されることです。
Pierma、2016年

これはプロセスのほんの一部です。私はこれらのマップを約1000個持っているので、プロセスを自動化すると非常に役立ちます。
16年

引き続き同じエラーが発生します->「1-"WITH"付近:構文エラー」。各レイヤーのローカル名をgrayLayerとredLayerに接続しました。ローカル名は私が使用すべきものですか?すなわち:私は「Basins_800.geometry」のようなコードを持っているので、灰色の層は、「Basins_800」と表示される
dnormous

2

SeverityおよびBasins800シェープファイルへのリンクを見た後、必要なジオプロセスを理解することができました。私はコードを変更しました:

QGISを使用して、90%を超える別のベクターポリゴンレイヤーと重複しているポリゴンをプログラムで検索していますか

これを取得するため:

mapcanvas = iface.mapCanvas()

layers = mapcanvas.layers()

#for Severity
feats_lyr1 = [ feat for feat in layers[0].getFeatures() ]

#for Basins800
feats_lyr2 = [ feat for feat in layers[1].getFeatures() ]

selected_feats = []

print "processing..."

for i, feat1 in enumerate(feats_lyr1):
    for j, feat2 in enumerate(feats_lyr2):
        if feat1.geometry().intersects(feat2.geometry()):
            area1 = feat1.geometry().intersection(feat2.geometry()).area()
            area2 = feat1.geometry().area()
            print i, j, area1, area2
    crit = area1/area2
    print crit
    if crit > 0.9:
        selected_feats.append(feat1)

epsg = layers[0].crs().postgisSrid()

uri = "Polygon?crs=epsg:" + str(epsg) + "&field=id:integer""&index=yes"

mem_layer = QgsVectorLayer(uri,
                           "mem_layer",
                           "memory")

prov = mem_layer.dataProvider()

for i, feat in enumerate(selected_feats):
    feat.setAttributes([i])

prov.addFeatures(selected_feats)

QgsMapLayerRegistry.instance().addMapLayer(mem_layer)

QGISのPythonコンソールでこれらのシェープファイルを使用してコードを実行した後、数分でPiermaと同様の結果が得られました。メモリレイヤーには31個のフィーチャがありました(彼が取得した29個のポリゴンとは異なります)。

ここに画像の説明を入力してください

機能には1901 * 3528 = 6706728の相互作用があるため、結果をデバッグしません。ただし、コードは有望に見えます。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.