如何在PyQGIS中使用QgsFeature更改属性的值?


12

我想更新一项功能的属性。但是,我不知道使用功能对象来更新它。我必须使用数据提供程序来更新它。

layers = QgsMapLayerRegistry.instance().mapLayersByName('my_line') 
layer = layers[0]
dp = layer.dataProvider()
it = dp.getFeatures()

for i in range(0, dp.featureCount()):
  feat = it.next()
  attrs = { 2 : 30 }
  layer.dataProvider().changeAttributeValues({ feat.id() : attrs })

我可以使用QgsFeature对象更改属性的值吗?

此外,是否可以使用迭代器对象进行循环?


如何在不使用索引的情况下更改值?我想通过命名它们的字段名来更改值。那会更舒服。非常感谢你!问候罗伯特
罗伯特BK

只需使用my_index = layer.fieldNameIndex("my_field_name")即可获取索引。
赫尔曼·卡里略

在这种情况下,我不能在字段中添加字符串我该怎么办?
Hamed Makian

如果您有新问题,请单击“ 提问”按钮提问。如果它有助于提供上下文,请包括此问题的链接。- 评分
丹ç

Hamed,欢迎您来到GIS Stack Exchange!由于已经回答了该问题,因此请在gis.stackexchange.com/questions/ask中作为一个单独的新问题提出您的问题。
cm1

Answers:


17

回答您的两个问题:

  1. 您可以从layer对象更改特征值,而无需访问dataProvider()

  2. 是的,您可以在for循环中使用迭代器。

检查以下代码:

layers = QgsMapLayerRegistry.instance().mapLayersByName('my_line') 
layer = layers[0]
it = layer.getFeatures()

layer.startEditing()
for feat in it:
  layer.changeAttributeValue(feat.id(), 2, 30)

layer.commitChanges()

这会将所有图层要素的第三个(索引2)字段值更新为30。


注意:正如您所指出的,由于某些原因,QgsFeature对象无法更新功能值,尽管API表示可以。


5

是的,但是您必须知道该字段的索引:

QgsFeature::setAttribute(int field,const QVariant & attr )  

您可以使用来获取字段QgsFeature::fields,然后对其进行遍历,直到找到所需QgsFeature::attribute(const QString & name )的字段或按名称查找字段索引。

使用QVariant的原因是setAttribute可以采用Integer,Float,Date和Text类型。QgsFeature.attribute(name)返回一个变体,如果找到了该属性,则它也返回int类型;如果找不到该属性,则返回其他类型..请在代码中注意这一点。可以尝试使用try..except块,尝试将其转换为int,除非type不是int。

您的功能可能不支持此方法。我采用的另一种方法是QgsVectorLayer::changeAttributeValue

self.canvas.currentLayer().changeAttributeValue(UpdateFeatureID,FieldToUpdate,self.CurrentWidget.text(),True)

这告诉图层更新特定的功能和特定的属性。在示例情况下,该值来自小部件。


我尝试过feat.setAttribute(1, QVariant(20))但系统说TypeError:PyQt4.QtCore.QVariant代表映射类型,无法实例化
wannik

feat.setAttribute(1,20)是我之前所做的。这就是把值“20”为属性1
迈克尔·史汀生

我试过了,feat.setAttribute(1, 20)但值没有改变。但是,我可以print(feat.attributes()[1])
wannik 2014年

查看编辑内容,也许您必须调用QgsVectorLayer.changeAttributeValue,它应该使用驱动程序进行更改。
Michael Stimson
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.