Make QgsVectorDataProvider::fields() return a copy

Implements a QGIS 3.0 TODO
This commit is contained in:
Nyall Dawson 2016-07-10 22:28:17 +10:00
parent 1bafa80089
commit e683101b10
33 changed files with 70 additions and 104 deletions

View File

@ -33,6 +33,14 @@ attributeIndexes(), pkAttributeIndexes(), isSaveAndLoadStyleToDBSupported()</li>
</li>
</ul>
\subsection qgis_api_break_3_0_DataProviders Data Providers
<ul>
<li>QgsVectorDataProvider::fields() now returns a copy, rather than a const reference. Since QgsFields
objects are implicitly shared, returning a copy helps simplify and make code more robust. This change
only affects third party c++ providers, and does not affect PyQGIS scripts.</li>
</ul>
\subsection qgis_api_break_3_0_QgsVectorFileWriter QgsVectorFileWriter
<ul>

View File

@ -116,11 +116,9 @@ class QgsVectorDataProvider : QgsDataProvider
virtual long featureCount() const = 0;
/**
* Return a map of indexes with field names for this layer
* @return map of fields
* @see QgsFields
* Returns the fields associated with this data provider.
*/
virtual const QgsFields &fields() const = 0;
virtual QgsFields fields() const = 0;
/**
* Return a short comment for the data that this provider is

View File

@ -533,13 +533,13 @@ QString QgsZonalStatistics::getUniqueFieldName( const QString& fieldName )
return fieldName;
}
const QgsFields& providerFields = dp->fields();
QgsFields providerFields = dp->fields();
QString shortName = fieldName.mid( 0, 10 );
bool found = false;
for ( int idx = 0; idx < providerFields.count(); ++idx )
{
if ( shortName == providerFields[idx].name() )
if ( shortName == providerFields.at( idx ).name() )
{
found = true;
break;
@ -559,7 +559,7 @@ QString QgsZonalStatistics::getUniqueFieldName( const QString& fieldName )
found = false;
for ( int idx = 0; idx < providerFields.count(); ++idx )
{
if ( shortName == providerFields[idx].name() )
if ( shortName == providerFields.at( idx ).name() )
{
n += 1;
if ( n < 9 )

View File

@ -266,10 +266,10 @@ QMap<QString, int> QgsVectorDataProvider::fieldNameMap() const
{
QMap<QString, int> resultMap;
const QgsFields& theFields = fields();
QgsFields theFields = fields();
for ( int i = 0; i < theFields.count(); ++i )
{
resultMap.insert( theFields[i].name(), i );
resultMap.insert( theFields.at( i ).name(), i );
}
return resultMap;
@ -431,20 +431,20 @@ void QgsVectorDataProvider::fillMinMaxCache() const
if ( !mCacheMinMaxDirty )
return;
const QgsFields& flds = fields();
QgsFields flds = fields();
for ( int i = 0; i < flds.count(); ++i )
{
if ( flds[i].type() == QVariant::Int )
if ( flds.at( i ).type() == QVariant::Int )
{
mCacheMinValues[i] = QVariant( INT_MAX );
mCacheMaxValues[i] = QVariant( INT_MIN );
}
else if ( flds[i].type() == QVariant::LongLong )
else if ( flds.at( i ).type() == QVariant::LongLong )
{
mCacheMinValues[i] = QVariant( std::numeric_limits<qlonglong>::max() );
mCacheMaxValues[i] = QVariant( std::numeric_limits<qlonglong>::min() );
}
else if ( flds[i].type() == QVariant::Double )
else if ( flds.at( i ).type() == QVariant::Double )
{
mCacheMinValues[i] = QVariant( DBL_MAX );
mCacheMaxValues[i] = QVariant( -DBL_MAX );
@ -470,7 +470,7 @@ void QgsVectorDataProvider::fillMinMaxCache() const
if ( varValue.isNull() )
continue;
if ( flds[*it].type() == QVariant::Int )
if ( flds.at( *it ).type() == QVariant::Int )
{
int value = varValue.toInt();
if ( value < mCacheMinValues[*it].toInt() )
@ -478,7 +478,7 @@ void QgsVectorDataProvider::fillMinMaxCache() const
if ( value > mCacheMaxValues[*it].toInt() )
mCacheMaxValues[*it] = value;
}
else if ( flds[*it].type() == QVariant::LongLong )
else if ( flds.at( *it ).type() == QVariant::LongLong )
{
qlonglong value = varValue.toLongLong();
if ( value < mCacheMinValues[*it].toLongLong() )
@ -486,7 +486,7 @@ void QgsVectorDataProvider::fillMinMaxCache() const
if ( value > mCacheMaxValues[*it].toLongLong() )
mCacheMaxValues[*it] = value;
}
else if ( flds[*it].type() == QVariant::Double )
else if ( flds.at( *it ).type() == QVariant::Double )
{
double value = varValue.toDouble();
if ( value < mCacheMinValues[*it].toDouble() )

View File

@ -166,12 +166,9 @@ class CORE_EXPORT QgsVectorDataProvider : public QgsDataProvider
virtual long featureCount() const = 0;
/**
* Return a map of indexes with field names for this layer
* @return map of fields
* @see QgsFields
* Returns the fields associated with this data provider.
*/
// TODO QGIS 3: return by value
virtual const QgsFields &fields() const = 0;
virtual QgsFields fields() const = 0;
/**
* Return a short comment for the data that this provider is

View File

@ -27,7 +27,7 @@ QgsVirtualLayerDefinition QgsVirtualLayerDefinitionUtils::fromJoinedLayer( QgsVe
QStringList columns;
// look for the uid
const QgsFields& fields = layer->dataProvider()->fields();
QgsFields fields = layer->dataProvider()->fields();
{
QgsAttributeList pk = layer->dataProvider()->pkAttributeIndexes();
if ( pk.size() == 1 )

View File

@ -282,11 +282,11 @@ bool eVisGenericEventBrowserGui::initBrowser()
return false;
}
const QgsFields& myFields = mDataProvider->fields();
QgsFields myFields = mDataProvider->fields();
mIgnoreEvent = true; //Ignore indexChanged event when adding items to combo boxes
for ( int x = 0; x < myFields.count(); x++ )
{
QString name = myFields[x].name();
QString name = myFields.at( x ).name();
cboxEventImagePathField->addItem( name );
cboxCompassBearingField->addItem( name );
cboxCompassOffsetField->addItem( name );
@ -594,13 +594,13 @@ void eVisGenericEventBrowserGui::loadRecord()
QString myCompassBearingField = cboxCompassBearingField->currentText();
QString myCompassOffsetField = cboxCompassOffsetField->currentText();
QString myEventImagePathField = cboxEventImagePathField->currentText();
const QgsFields& myFields = mDataProvider->fields();
QgsFields myFields = mDataProvider->fields();
QgsAttributes myAttrs = myFeature->attributes();
//loop through the attributes and display their contents
for ( int i = 0; i < myAttrs.count(); ++i )
{
QStringList myValues;
QString fieldName = myFields[i].name();
QString fieldName = myFields.at( i ).name();
myValues << fieldName << myAttrs.at( i ).toString();
QTreeWidgetItem* myItem = new QTreeWidgetItem( myValues );
if ( fieldName == myEventImagePathField )
@ -836,7 +836,7 @@ void eVisGenericEventBrowserGui::on_cboxEventImagePathField_currentIndexChanged(
{
mConfiguration.setEventImagePathField( cboxEventImagePathField->currentText() );
const QgsFields& myFields = mDataProvider->fields();
QgsFields myFields = mDataProvider->fields();
QgsFeature* myFeature = featureAtId( mFeatureIds.at( mCurrentFeatureIndex ) );
if ( !myFeature )
@ -864,7 +864,7 @@ void eVisGenericEventBrowserGui::on_cboxCompassBearingField_currentIndexChanged(
{
mConfiguration.setCompassBearingField( cboxCompassBearingField->currentText() );
const QgsFields& myFields = mDataProvider->fields();
QgsFields myFields = mDataProvider->fields();
QgsFeature* myFeature = featureAtId( mFeatureIds.at( mCurrentFeatureIndex ) );
if ( !myFeature )
@ -873,7 +873,7 @@ void eVisGenericEventBrowserGui::on_cboxCompassBearingField_currentIndexChanged(
QgsAttributes myAttrs = myFeature->attributes();
for ( int i = 0; i < myAttrs.count(); ++i )
{
if ( myFields[i].name() == cboxCompassBearingField->currentText() )
if ( myFields.at( i ).name() == cboxCompassBearingField->currentText() )
{
mCompassBearing = myAttrs.at( i ).toDouble();
}
@ -892,7 +892,7 @@ void eVisGenericEventBrowserGui::on_cboxCompassOffsetField_currentIndexChanged(
{
mConfiguration.setCompassOffsetField( cboxCompassOffsetField->currentText() );
const QgsFields& myFields = mDataProvider->fields();
QgsFields myFields = mDataProvider->fields();
QgsFeature* myFeature = featureAtId( mFeatureIds.at( mCurrentFeatureIndex ) );
if ( !myFeature )
@ -901,7 +901,7 @@ void eVisGenericEventBrowserGui::on_cboxCompassOffsetField_currentIndexChanged(
QgsAttributes myAttrs = myFeature->attributes();
for ( int i = 0; i < myAttrs.count(); ++i )
{
if ( myFields[i].name() == cboxCompassOffsetField->currentText() )
if ( myFields.at( i ).name() == cboxCompassOffsetField->currentText() )
{
mCompassOffset = myAttrs.at( i ).toDouble();
}

View File

@ -43,7 +43,7 @@ class QgsAfsProvider : public QgsVectorDataProvider
QgsFeatureIterator getFeatures( const QgsFeatureRequest& request = QgsFeatureRequest() ) const override;
QGis::WkbType geometryType() const override { return static_cast<QGis::WkbType>( mGeometryType ); }
long featureCount() const override { return mObjectIds.size(); }
const QgsFields &fields() const override { return mFields; }
QgsFields fields() const override { return mFields; }
/* Read only for the moment
bool addFeatures( QgsFeatureList &flist ) override{ return false; }
bool deleteFeatures( const QgsFeatureIds &id ) override{ return false; }

View File

@ -494,7 +494,7 @@ long QgsDb2Provider::featureCount() const
}
}
const QgsFields &QgsDb2Provider::fields() const
QgsFields QgsDb2Provider::fields() const
{
return mAttributeFields;
}

View File

@ -70,11 +70,8 @@ class QgsDb2Provider : public QgsVectorDataProvider
*/
void updateStatistics() const;
/**
* Return a map of indexes with field names for this layer.
* @return map of fields
*/
virtual const QgsFields &fields() const override;
virtual QgsFields fields() const override;
virtual QgsCoordinateReferenceSystem crs() const override;
virtual QgsRectangle extent() const override;

View File

@ -1135,7 +1135,7 @@ long QgsDelimitedTextProvider::featureCount() const
}
const QgsFields & QgsDelimitedTextProvider::fields() const
QgsFields QgsDelimitedTextProvider::fields() const
{
return attributeFields;
}

View File

@ -101,11 +101,7 @@ class QgsDelimitedTextProvider : public QgsVectorDataProvider
*/
virtual long featureCount() const override;
/**
* Return a map of indexes with field names for this layer
* @return map of fields
*/
virtual const QgsFields & fields() const override;
virtual QgsFields fields() const override;
/** Returns a bitmask containing the supported capabilities
* Note, some capabilities may change depending on whether

View File

@ -171,7 +171,7 @@ long QgsGPXProvider::featureCount() const
}
const QgsFields& QgsGPXProvider::fields() const
QgsFields QgsGPXProvider::fields() const
{
return attributeFields;
}

View File

@ -69,10 +69,7 @@ class QgsGPXProvider : public QgsVectorDataProvider
*/
virtual long featureCount() const override;
/**
* Get the field information for the layer
*/
virtual const QgsFields& fields() const override;
virtual QgsFields fields() const override;
/**
* Adds a list of features

View File

@ -453,7 +453,7 @@ long QgsGrassProvider::featureCount() const
return mNumberFeatures;
}
const QgsFields & QgsGrassProvider::fields() const
QgsFields QgsGrassProvider::fields() const
{
if ( isTopoType() )
{

View File

@ -88,10 +88,7 @@ class GRASS_LIB_EXPORT QgsGrassProvider : public QgsVectorDataProvider
virtual QgsRectangle extent() const override;
/**
* Get the field information for the layer
*/
const QgsFields & fields() const override;
QgsFields fields() const override;
// ! Key (category) field index
int keyField();

View File

@ -309,7 +309,7 @@ long QgsMemoryProvider::featureCount() const
return count;
}
const QgsFields & QgsMemoryProvider::fields() const
QgsFields QgsMemoryProvider::fields() const
{
return mFields;
}

View File

@ -61,12 +61,7 @@ class QgsMemoryProvider : public QgsVectorDataProvider
*/
virtual long featureCount() const override;
/**
* Return a map of indexes with field names for this layer
* @return map of fields
*/
virtual const QgsFields & fields() const override;
virtual QgsFields fields() const override;
/**
* Adds a list of features

View File

@ -778,7 +778,7 @@ long QgsMssqlProvider::featureCount() const
}
}
const QgsFields & QgsMssqlProvider::fields() const
QgsFields QgsMssqlProvider::fields() const
{
return mAttributeFields;
}

View File

@ -93,11 +93,7 @@ class QgsMssqlProvider : public QgsVectorDataProvider
/** Update the extent, feature count, wkb type and srid for this layer */
void UpdateStatistics( bool estimate ) const;
/**
* Return a map of indexes with field names for this layer
* @return map of fields
*/
virtual const QgsFields & fields() const override;
virtual QgsFields fields() const override;
QString subsetString() const override;

View File

@ -1035,7 +1035,7 @@ long QgsOgrProvider::featureCount() const
}
const QgsFields & QgsOgrProvider::fields() const
QgsFields QgsOgrProvider::fields() const
{
return mAttributeFields;
}
@ -1666,7 +1666,7 @@ bool QgsOgrProvider::createAttributeIndex( int field )
QByteArray quotedLayerName = quotedIdentifier( OGR_FD_GetName( OGR_L_GetLayerDefn( ogrOrigLayer ) ) );
QByteArray dropSql = "DROP INDEX ON " + quotedLayerName;
OGR_DS_ExecuteSQL( ogrDataSource, dropSql.constData(), OGR_L_GetSpatialFilter( ogrOrigLayer ), nullptr );
QByteArray createSql = "CREATE INDEX ON " + quotedLayerName + " USING " + mEncoding->fromUnicode( fields()[field].name() );
QByteArray createSql = "CREATE INDEX ON " + quotedLayerName + " USING " + mEncoding->fromUnicode( fields().at( field ).name() );
OGR_DS_ExecuteSQL( ogrDataSource, createSql.constData(), OGR_L_GetSpatialFilter( ogrOrigLayer ), nullptr );
QFileInfo fi( mFilePath ); // to get the base name

View File

@ -117,10 +117,7 @@ class QgsOgrProvider : public QgsVectorDataProvider
*/
virtual long featureCount() const override;
/**
* Get the field information for the layer
*/
virtual const QgsFields & fields() const override;
virtual QgsFields fields() const override;
virtual QgsRectangle extent() const override;

View File

@ -703,7 +703,7 @@ const QgsField &QgsPostgresProvider::field( int index ) const
return mAttributeFields[index];
}
const QgsFields & QgsPostgresProvider::fields() const
QgsFields QgsPostgresProvider::fields() const
{
return mAttributeFields;
}

View File

@ -133,11 +133,7 @@ class QgsPostgresProvider : public QgsVectorDataProvider
*/
void determinePrimaryKeyFromUriKeyColumn();
/**
* Get the field information for the layer
* @return vector of QgsField objects
*/
const QgsFields &fields() const override;
QgsFields fields() const override;
/**
* Return a short comment for the data that this provider is

View File

@ -3365,7 +3365,7 @@ QString QgsSpatiaLiteProvider::description() const
return SPATIALITE_DESCRIPTION;
} // QgsSpatiaLiteProvider::description()
const QgsFields& QgsSpatiaLiteProvider::fields() const
QgsFields QgsSpatiaLiteProvider::fields() const
{
return mAttributeFields;
}

View File

@ -124,11 +124,7 @@ class QgsSpatiaLiteProvider: public QgsVectorDataProvider
*/
virtual void updateExtents() override;
/**
* Get the field information for the layer
* @return vector of QgsField objects
*/
const QgsFields & fields() const override;
QgsFields fields() const override;
QVariant minimumValue( int index ) const override;
QVariant maximumValue( int index ) const override;

View File

@ -553,7 +553,7 @@ void QgsVirtualLayerProvider::invalidateStatistics()
mCachedStatistics = false;
}
const QgsFields & QgsVirtualLayerProvider::fields() const
QgsFields QgsVirtualLayerProvider::fields() const
{
return mDefinition.fields();
}

View File

@ -63,11 +63,7 @@ class QgsVirtualLayerProvider: public QgsVectorDataProvider
virtual bool supportsSubsetString() const override { return true; }
/**
* Get the field information for the layer
* @return vector of QgsField objects
*/
const QgsFields & fields() const override;
QgsFields fields() const override;
bool isValid() const override;

View File

@ -792,7 +792,7 @@ QgsWFSFeatureIterator::QgsWFSFeatureIterator( QgsWFSFeatureSource* source,
if ( mRequest.flags() & QgsFeatureRequest::SubsetOfAttributes )
{
const QgsFields & dataProviderFields = mShared->mCacheDataProvider->fields();
QgsFields dataProviderFields = mShared->mCacheDataProvider->fields();
QgsAttributeList cacheSubSet;
Q_FOREACH ( int i, mRequest.subsetOfAttributes() )
{

View File

@ -724,7 +724,7 @@ long QgsWFSProvider::featureCount() const
return mShared->getFeatureCount();
}
const QgsFields& QgsWFSProvider::fields() const
QgsFields QgsWFSProvider::fields() const
{
return mShared->mFields;
}

View File

@ -74,7 +74,7 @@ class QgsWFSProvider : public QgsVectorDataProvider
QGis::WkbType geometryType() const override;
long featureCount() const override;
const QgsFields& fields() const override;
QgsFields fields() const override;
virtual QgsCoordinateReferenceSystem crs() const override;

View File

@ -581,7 +581,7 @@ QSet<QString> QgsWFSSharedData::getExistingCachedGmlIds( const QVector<QgsWFSFea
bool first = true;
QSet<QString> setExistingGmlIds;
const QgsFields & dataProviderFields = mCacheDataProvider->fields();
QgsFields dataProviderFields = mCacheDataProvider->fields();
const int gmlidIdx = dataProviderFields.indexFromName( QgsWFSConstants::FIELD_GMLID );
// To avoid excessive memory consumption in expression building, do not
@ -632,7 +632,7 @@ QSet<QString> QgsWFSSharedData::getExistingCachedMD5( const QVector<QgsWFSFeatur
bool first = true;
QSet<QString> setExistingMD5;
const QgsFields & dataProviderFields = mCacheDataProvider->fields();
QgsFields dataProviderFields = mCacheDataProvider->fields();
const int md5Idx = dataProviderFields.indexFromName( QgsWFSConstants::FIELD_MD5 );
// To avoid excessive memory consumption in expression building, do not
@ -685,7 +685,7 @@ QString QgsWFSSharedData::findGmlId( QgsFeatureId fid )
QgsFeatureRequest request;
request.setFilterFid( fid );
const QgsFields & dataProviderFields = mCacheDataProvider->fields();
QgsFields dataProviderFields = mCacheDataProvider->fields();
int gmlidIdx = dataProviderFields.indexFromName( QgsWFSConstants::FIELD_GMLID );
QgsAttributeList attList;
@ -765,7 +765,7 @@ bool QgsWFSSharedData::changeAttributeValues( const QgsChangedAttributesMap &att
if ( !mCacheDataProvider )
return false;
const QgsFields & dataProviderFields = mCacheDataProvider->fields();
QgsFields dataProviderFields = mCacheDataProvider->fields();
QgsChangedAttributesMap newMap;
for ( QgsChangedAttributesMap::const_iterator iter = attr_map.begin(); iter != attr_map.end(); ++iter )
{
@ -812,7 +812,7 @@ void QgsWFSSharedData::serializeFeatures( QVector<QgsWFSFeatureGmlIdPair>& featu
}
QgsFeatureList featureListToCache;
const QgsFields & dataProviderFields = mCacheDataProvider->fields();
QgsFields dataProviderFields = mCacheDataProvider->fields();
int gmlidIdx = dataProviderFields.indexFromName( QgsWFSConstants::FIELD_GMLID );
Q_ASSERT( gmlidIdx >= 0 );
int genCounterIdx = dataProviderFields.indexFromName( QgsWFSConstants::FIELD_GEN_COUNTER );

View File

@ -1575,7 +1575,7 @@ QDomDocument QgsWFSServer::transaction( const QString& requestBody )
}
// Update the features
const QgsFields& fields = provider->fields();
QgsFields fields = provider->fields();
QMap<QString, int> fieldMap = provider->fieldNameMap();
QMap<QString, int>::const_iterator fieldMapIt;
QString fieldName;
@ -1605,7 +1605,7 @@ QDomDocument QgsWFSServer::transaction( const QString& requestBody )
{
continue;
}
const QgsField& field = fields[fieldMapIt.value()];
const QgsField& field = fields.at( fieldMapIt.value() );
if ( field.type() == 2 )
layer->changeAttributeValue( *fidIt, fieldMapIt.value(), it.value().toInt( &conversionSuccess ) );
else if ( field.type() == 6 )
@ -1694,7 +1694,7 @@ QDomDocument QgsWFSServer::transaction( const QString& requestBody )
if ( cap & QgsVectorDataProvider::AddFeatures )
{
// Get Layer Field Information
const QgsFields& fields = provider->fields();
QgsFields fields = provider->fields();
QMap<QString, int> fieldMap = provider->fieldNameMap();
QMap<QString, int>::const_iterator fieldMapIt;
@ -1739,7 +1739,7 @@ QDomDocument QgsWFSServer::transaction( const QString& requestBody )
{
continue;
}
const QgsField& field = fields[fieldMapIt.value()];
const QgsField& field = fields.at( fieldMapIt.value() );
QString attrValue = currentAttributeElement.text();
int attrType = field.type();
QgsMessageLog::logMessage( QString( "attr: name=%1 idx=%2 value=%3" ).arg( attrName ).arg( fieldMapIt.value() ).arg( attrValue ) );
@ -1845,7 +1845,7 @@ QgsFeatureIds QgsWFSServer::getFeatureIdsFromFilter( const QDomElement& filterEl
throw QgsMapServiceException( "RequestNotWellFormed", filter->parserErrorString() );
}
QgsFeature feature;
const QgsFields& fields = provider->fields();
QgsFields fields = provider->fields();
QgsFeatureIterator fit = layer->getFeatures();
QgsExpressionContext context = QgsExpressionContextUtils::createFeatureBasedContext( feature, fields );