3
\$\begingroup\$

In a QGIS 2.0 plugin for windows, I calculate length and update a field with the values. It works, but takes a lot of time. Execution for this part only takes about ten minutes. Can anyone suggest anything to speed things up?

def calculatelength(self):
    idx = self.resLayer.fieldNameIndex('Longueur')
    caps = self.resLayer.dataProvider().capabilities()
    features = self.resLayer.getFeatures()
    for feature in features:
        if caps & QgsVectorDataProvider.ChangeAttributeValues:
            fid = feature.id()
            flen = feature.geometry().length()
            attrs = {idx : flen}
            self.resLayer.dataProvider().changeAttributeValues({fid : attrs})
\$\endgroup\$

1 Answer 1

2
\$\begingroup\$

I'm not familiar with the libraries in question, but it seems to me that you could take a couple of things out from the for loop:

  1. The if condition does not look like it would change between iterations.
  2. As changeAttributeValues takes a dictionary argument, I would expect it to handle a dictionary with multiple keys as well. Construct a dict with all fid : attrs pairs in the loop and make just one function call after.

My proposal:

def calculatelength(self):
    idx = self.resLayer.fieldNameIndex('Longueur')
    caps = self.resLayer.dataProvider().capabilities()
    if caps & QgsVectorDataProvider.ChangeAttributeValues:
        features = self.resLayer.getFeatures()
        feature_attrs = {}
        for feature in features:
            fid = feature.id()
            flen = feature.geometry().length()
            feature_attrs[fid] = {idx : flen}
        self.resLayer.dataProvider().changeAttributeValues(feature_attrs)
\$\endgroup\$

Your Answer

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

Not the answer you're looking for? Browse other questions tagged or ask your own question.