|
41 | 41 |
|
42 | 42 | QgsOgrFeatureIterator::QgsOgrFeatureIterator( QgsOgrFeatureSource *source, bool ownSource, const QgsFeatureRequest &request )
|
43 | 43 | : QgsAbstractFeatureIteratorFromSource<QgsOgrFeatureSource>( source, ownSource, request )
|
44 |
| - , mFilterFids( mRequest.filterFids() ) |
45 |
| - , mFilterFidsIt( mFilterFids.constBegin() ) |
46 | 44 | , mSharedDS( source->mSharedDS )
|
47 | 45 | , mFirstFieldIsFid( source->mFirstFieldIsFid )
|
48 | 46 | , mFieldsWithoutFid( source->mFieldsWithoutFid )
|
49 | 47 | {
|
| 48 | + for ( const auto &id : mRequest.filterFids() ) |
| 49 | + { |
| 50 | + mFilterFids.insert( id ); |
| 51 | + } |
| 52 | + mFilterFidsIt = mFilterFids.begin(); |
| 53 | + |
50 | 54 | // Since connection timeout for OGR connections is problematic and can lead to crashes, disable for now.
|
51 | 55 | mRequest.setTimeout( -1 );
|
52 | 56 | if ( mSharedDS )
|
@@ -235,7 +239,47 @@ bool QgsOgrFeatureIterator::fetchFeatureWithId( QgsFeatureId id, QgsFeature &fea
|
235 | 239 | {
|
236 | 240 | feature.setValid( false );
|
237 | 241 | gdal::ogr_feature_unique_ptr fet;
|
238 |
| - fet.reset( OGR_L_GetFeature( mOgrLayer, FID_TO_NUMBER( id ) ) ); |
| 242 | + |
| 243 | +#if GDAL_VERSION_NUM >= GDAL_COMPUTE_VERSION(2,2,0) |
| 244 | + if ( !QgsOgrProviderUtils::canDriverShareSameDatasetAmongLayers( mSource->mDriverName ) ) |
| 245 | + { |
| 246 | + OGRLayerH nextFeatureBelongingLayer; |
| 247 | + bool found = false; |
| 248 | + // First pass: try to read from the last feature, in the hope the dataset |
| 249 | + // returns them in increasing feature id number (and as we use a std::set |
| 250 | + // for mFilterFids, we get them in increasing number by the iterator) |
| 251 | + // Second pass: reset before reading |
| 252 | + for ( int passNumber = 0; passNumber < 2; passNumber++ ) |
| 253 | + { |
| 254 | + while ( fet.reset( GDALDatasetGetNextFeature( |
| 255 | + mConn->ds, &nextFeatureBelongingLayer, nullptr, nullptr, nullptr ) ), fet ) |
| 256 | + { |
| 257 | + if ( nextFeatureBelongingLayer == mOgrLayer ) |
| 258 | + { |
| 259 | + if ( OGR_F_GetFID( fet.get() ) == FID_TO_NUMBER( id ) ) |
| 260 | + { |
| 261 | + found = true; |
| 262 | + break; |
| 263 | + } |
| 264 | + } |
| 265 | + } |
| 266 | + if ( found || passNumber == 1 ) |
| 267 | + { |
| 268 | + break; |
| 269 | + } |
| 270 | + GDALDatasetResetReading( mConn->ds ); |
| 271 | + } |
| 272 | + |
| 273 | + if ( !found ) |
| 274 | + { |
| 275 | + return false; |
| 276 | + } |
| 277 | + } |
| 278 | + else |
| 279 | +#endif |
| 280 | + { |
| 281 | + fet.reset( OGR_L_GetFeature( mOgrLayer, FID_TO_NUMBER( id ) ) ); |
| 282 | + } |
239 | 283 |
|
240 | 284 | if ( !fet )
|
241 | 285 | {
|
@@ -281,10 +325,10 @@ bool QgsOgrFeatureIterator::fetchFeature( QgsFeature &feature )
|
281 | 325 | }
|
282 | 326 | else if ( mRequest.filterType() == QgsFeatureRequest::FilterFids )
|
283 | 327 | {
|
284 |
| - while ( mFilterFidsIt != mFilterFids.constEnd() ) |
| 328 | + while ( mFilterFidsIt != mFilterFids.end() ) |
285 | 329 | {
|
286 | 330 | QgsFeatureId nextId = *mFilterFidsIt;
|
287 |
| - mFilterFidsIt++; |
| 331 | + ++mFilterFidsIt; |
288 | 332 |
|
289 | 333 | if ( fetchFeatureWithId( nextId, feature ) )
|
290 | 334 | return true;
|
@@ -351,7 +395,7 @@ bool QgsOgrFeatureIterator::rewind()
|
351 | 395 |
|
352 | 396 | resetReading();
|
353 | 397 |
|
354 |
| - mFilterFidsIt = mFilterFids.constBegin(); |
| 398 | + mFilterFidsIt = mFilterFids.begin(); |
355 | 399 |
|
356 | 400 | return true;
|
357 | 401 | }
|
|
0 commit comments