Excluindo recursos selecionados usando o PyQGIS?

8

Eu tenho um shapefile com apenas um DN de campo . Gostaria de excluir todos os recursos que não possuem valor específico do campo. Digamos que o DN possa ser 1,2 ou 3.

Até agora, pude descobrir como selecionar Recursos e como excluir recursos, mas não consegui combiná-los. Digamos que eu queira que apenas os recursos com DN = 3 permaneçam:

Seleção dos recursos encontrados aqui , no entanto, não sei se ele faz o que deveria fazer, pois não encontrei a maneira de verificar o que está dentro.

select = layer.getFeatures(QgsFeatureRequest().setFilterExpression(u'"DN"!=3'))

excluir recursos encontrados aqui

res = Ilayer.dataProvider().deleteFeatures()

Tanto quanto eu sei, o deleteFeatures()requer IDs dos recursos, mas não tenho idéia de como obtê-los a partir do selectque é QgsFeatureIterator.

MasterPJ
fonte

Respostas:

18

Você pode percorrer o iterador e obter .id()todos os recursos nele:

with edit(layer):
    # build a request to filter the features based on an attribute
    request = QgsFeatureRequest().setFilterExpression('"DN" != 3')

    # we don't need attributes or geometry, skip them to minimize overhead.
    # these lines are not strictly required but improve performance
    request.setSubsetOfAttributes([])
    request.setFlags(QgsFeatureRequest.NoGeometry)

    # loop over the features and delete
    for f in layer.getFeatures(request):
        layer.deleteFeature(f.id())

Ou com QGIS <2.12

request = QgsFeatureRequest().setFilterExpression('"DN" != 3')
request.setSubsetOfAttributes([])
request.setFlags(QgsFeatureRequest.NoGeometry)
ids = [f.id() for f in layer.getFeatures(request)]
layer.startEditing()
for fid in ids:
    layer.deleteFeature(fid)
layer.commitChanges()
Matthias Kuhn
fonte
Obrigado, foi isso! Acabei de notar que a FilterExpression estava incorreta (não é necessário usar 'DN' = 2 || "DN" = 1 ', mas usar' DN "! = 3 '). Se você editar sua resposta para não confundir outros espectadores, edite sua resposta.
precisa saber é o seguinte
não é layer.dataProvider (). deleteFeatures (ids)?
mbernasocchi
É possível usar o dataProvider (), mas eu prefiro trabalhar diretamente na camada, pois assim as alterações são comunicadas internamente (para a tela do mapa, tabela de atributos ...) e outros motivos .
Matthias Kuhn
2
O layer.dataProvider (). deleteFeatures (ids) gerou falhas para mim quando o layer.deleteFeature (fid) não ... Falhas ruins. O tipo que causa uma falha de seg e mata qgis. O tipo que leva 6 horas para encontrar ... fique com a resposta postada aqui. Me chateia, porque layer.dataProvider (). DeleteFeatures (ids) é tudo através do meu código e agora tenho que corrigir tudo.
Sr. Roxo