2

I'm trying to use QGIS to loop through a set of points, find their elevation from a DEM and use that value to update the point layer's attribute table. The loop works fine until I try to use changeAttributeValues(), and I can change the attribute values outside of the loop, but when I try to put the two together I cause a dump.

while provider.nextFeature(feat):
 geom = feat.geometry()
 x = geom.asPoint()
 res, ident = rlayer.identify(QgsPoint(x))
 for (k,v) in ident.iteritems():
 elevation = float(v)
 attrs = { 2 : elevation }
 caps = vlayer.dataProvider().capabilities()
 if caps & QgsVectorDataProvider.ChangeAttributeValues:
 vlayer.dataProvider().changeAttributeValues({ fid : attrs })

This causes the following error in Linux:

*** glibc detected *** python2: free(): invalid pointer: 0x00000000024655b8 ***

Edit:

The problem isn't the loop, it is now I'm calling changeAttributeValues(). I've simplified the script down to just update a single point and it causes the same core dump. Here's the updated script:

#!/usr/bin/env python2
# -*- coding: utf-8 -*-
from qgis.core import *
import qgis.utils
#initializes QGIS and points python to where it can find QGIS's stuff
QgsApplication.setPrefixPath("/usr/", True)
QgsApplication.initQgis()
vlayer = QgsVectorLayer("/gis/vector/elev_pts.shp", "elev_pts", "ogr")
if not vlayer.isValid():
 print "Layer did not load!"
vlayer.dataProvider().changeAttributeValues({ 0: 2: 432.1 })
QgsApplication.exitQgis()
asked Oct 2, 2012 at 21:38
2
  • Is that if meant to be inside the for? Commented Oct 2, 2012 at 22:08
  • 1
    Sorry, no. The indents got thrown off for the if statement when I brought it in. It's there to make sure I can change the attributes on the vector layer, it's not needed for this but I put it in there in case I decide to expand this into a plugin later. Commented Oct 3, 2012 at 0:46

2 Answers 2

4

Figured it out, by using changeAttributeValue() instead of changeAttributeValues() I got the script to work. Here's a loop that works:

# Loop through each point feature
while provider.nextFeature(feat):
 geom = feat.geometry()
 x = geom.asPoint()
 #Get the raster value of the cell under the vector point
 res, ident = rlayer.identify(QgsPoint(x))
 #The key is the raster band, and the value is the cell's raster value
 for (k,v) in ident.iteritems():
 elevation = float(v)
 fid = int(feat.id())
 vlayer.startEditing()
 vlayer.changeAttributeValue(fid, 2, elevation)
 vlayer.commitChanges()

This only works if the raster is a single band raster.

answered Oct 3, 2012 at 18:13
1

What I see from your code: attrs is a dict that always has the key 2. When you use changeAttributeValues you also pass a dict to the function (which might be correct but is very unusual). But

({ fid : attrs }) equals ({ fid : { 2 : elevation }}) 

Is this maybe causing the problem?

answered Oct 3, 2012 at 11:31
3
  • I was working off of an example from the pyqgis cookbook and they show to use a dict as the second parameter. The 2 in this case is the index for the field to be modified and the second element, in this case the value of elevation, is the new value for that field. Fid here is the feature ID for the feature getting the new value. Commented Oct 3, 2012 at 12:45
  • So if you hard code the call, e.g. vlayer.dataProvider().changeAttributeValues({ fid : {2: 4.0}}) it works? And what does fid = feat.id() return by the way? Commented Oct 3, 2012 at 13:19
  • Yeah, I just tried it in the Python console and it updated the correct record with the correct value. fid = feat.id() returned type long, changed it to fid = int(feat.id()) and it still core dumps. Commented Oct 3, 2012 at 13:31

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

By clicking "Post Your Answer", you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.