1

I have a shapefile and I need to update a field with calculation results. In the calculation I'm iterating through two list with equal items as features of the shapefile. The sum of the list items gets multiplied with an integer value (constant). The field name which needs to be updated is "SH".

Here is how I tried solving it with some example data:

a = [134.24, 134.24, 134.24, 134.99]
b = [58.848430067837946, 70.46615125391358, 63.02756211443306, 60.662300968221174]
c = 0.6673779977746334
newlayer = iface.addVectorLayer(outfile_rel_revised,"", "ogr")
newlayer.setCrs(crsSrc)
with edit(newlayer):
 for rel_feature in newlayer.getFeatures():
 for i in a:
 for j in b:
 rel_feature['SH'] = ((i + j)* c)
 newlayer.updateFeature(rel_feature)
 break 

If I run this, I get no error but the field is not updated. For example the calculation for feature 1 should look like this: (134.24 + 58.848430067837946)*0.6673779977746334

The finished result should look like this:

enter image description here

Taras
35.7k5 gold badges77 silver badges151 bronze badges
asked May 1, 2022 at 17:47
3
  • 1
    I guess you referenced newlayer (e.g. newlayer = iface.activeLayer())? Apart from that you could also assign a 5 to every feature directly without calculating ;) Commented May 1, 2022 at 17:54
  • The flow of control in this code doesn't make much sense. The end result should be the same as assigning a value of 5 to all rows once (due to the break, the j loop only fires once) Commented May 1, 2022 at 19:31
  • Thanks for responding. I update the question, I hope it's more clear what I want the code to do:) Commented May 1, 2022 at 21:16

1 Answer 1

2

Try this logic:

a = [134.24, 134.24, 134.24, 134.99]
b = [58.848430067837946, 70.46615125391358, 63.02756211443306, 60.662300968221174]
c = 0.6673779977746334
newlayer = iface.activeLayer()
with edit(newlayer):
 for i,rel_feature in enumerate(newlayer.getFeatures()):
 rel_feature['SH'] = round((a[i] + b[i])*c,2)
 newlayer.updateFeature(rel_feature)

Make sure your file is not write protected and the field (SH) is of type real.

This should actually work. If for some reason it does not update the file, you can give changeAttributeValue() method a try:

a = [134.24, 134.24, 134.24, 134.99]
b = [58.848430067837946, 70.46615125391358, 63.02756211443306, 60.662300968221174]
c = 0.6673779977746334
newlayer = iface.activeLayer()
with edit(newlayer):
 for i,rel_feature in enumerate(newlayer.getFeatures()):
 result = round((a[i] + b[i])*c,2)
 newlayer.changeAttributeValue(rel_feature.id(), newlayer.fields().indexOf('SH'), result)

With this kind of logic an order by request might make sense:

a = [134.24, 134.24, 134.24, 134.99]
b = [58.848430067837946, 70.46615125391358, 63.02756211443306, 60.662300968221174]
c = 0.6673779977746334
newlayer = iface.activeLayer()
request = QgsFeatureRequest()
clause = QgsFeatureRequest.OrderByClause('id', ascending=True)
orderby = QgsFeatureRequest.OrderBy([clause])
request.setOrderBy(orderby)
with edit(newlayer):
 for i,rel_feature in enumerate(newlayer.getFeatures(request)):
 result = round((a[i] + b[i])*c,2)
 newlayer.changeAttributeValue(rel_feature.id(), newlayer.fields().indexOf('SH'), result)
answered May 1, 2022 at 21:29
3
  • Thank you!! The first code worked fine on the first try, but then I tried to extent your code to get another two fields updated. Like this: with edit(newlayer): for i,rel_feature in enumerate(newlayer.getFeatures()): rel_feature['SH'] = round((a[i] + b[i])*c,2) rel_feature['SH30'] = round((a[i] + b[i] + (wind1 * 100))*c,2) rel_feature['SH50'] = round((a[i] + b[i] + (wind2 * 100))*c,2) newlayer.updateFeature(rel_feature) now I get this error TypeError: unsupported operand type(s) for *: 'float' and 'QgsColorRampShader'. Any ideas? Commented May 2, 2022 at 16:19
  • @Simon I guess either variable wind1 or wind2 contains a QgsColorRampShader object. Make sure it contains a numerical value. The error just says that you cannot multiply a QgsColorRampShader object. Commented May 2, 2022 at 18:55
  • I solved the error, but the fields won't update anymore. If I print the result it's correct but it doesn't update. I also tried to write the result into a list and update this way [gis.stackexchange.com/a/286780/204059] but also no update. I updated another field of this layer with this logic [gis.stackexchange.com/a/429009/204059] and had no problems. I don't unterstand why it doesn't update the fields!! Commented May 2, 2022 at 20:23

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.