QGIS API Documentation  3.37.0-Master (a5b4d9743e8)
qgsvectorlayercache.h
Go to the documentation of this file.
1 /***************************************************************************
2  qgsvectorlayercache.h
3  Cache features of a vector layer
4  -------------------
5  begin : January 2013
6  copyright : (C) Matthias Kuhn
7  email : matthias at opengis dot ch
8 
9  ***************************************************************************
10  * *
11  * This program is free software; you can redistribute it and/or modify *
12  * it under the terms of the GNU General Public License as published by *
13  * the Free Software Foundation; either version 2 of the License, or *
14  * (at your option) any later version. *
15  * *
16  ***************************************************************************/
17 
18 
19 #ifndef QgsVectorLayerCache_H
20 #define QgsVectorLayerCache_H
21 
22 #include "qgis_core.h"
23 #include "qgis_sip.h"
24 #include "qgsfield.h"
25 #include "qgsfeaturerequest.h"
26 #include "qgsfeatureiterator.h"
27 #include <unordered_set>
28 #include <deque>
29 #include <QCache>
30 
31 class QgsVectorLayer;
32 class QgsFeature;
35 
46 class CORE_EXPORT QgsVectorLayerCache : public QObject
47 {
48  Q_OBJECT
49 
50  private:
51 
57  class CORE_EXPORT QgsCachedFeature
58  {
59  public:
60 
68  QgsCachedFeature( const QgsFeature &feat, QgsVectorLayerCache *vlCache, bool allAttributesFetched )
69  : mCache( vlCache )
70  , mAllAttributesFetched( allAttributesFetched )
71  {
72  mFeature = new QgsFeature( feat );
73  }
74 
75  ~QgsCachedFeature()
76  {
77  // That's the reason we need this wrapper:
78  // Inform the cache that this feature has been removed
79  mCache->featureRemoved( mFeature->id() );
80  delete mFeature;
81  }
82 
83  inline const QgsFeature *feature() { return mFeature; }
84 
85  bool allAttributesFetched() const;
86 
87  private:
88  QgsFeature *mFeature = nullptr;
89  QgsVectorLayerCache *mCache = nullptr;
90  bool mAllAttributesFetched = true;
91 
92  friend class QgsVectorLayerCache;
93  Q_DISABLE_COPY( QgsCachedFeature )
94  };
95 
96  public:
97  QgsVectorLayerCache( QgsVectorLayer *layer, int cacheSize, QObject *parent SIP_TRANSFERTHIS = nullptr );
98  ~QgsVectorLayerCache() override;
99 
106  void setCacheSize( int cacheSize );
107 
115  int cacheSize();
116 
123  void setCacheGeometry( bool cacheGeometry );
124 
129  bool cacheGeometry() const { return mCacheGeometry; }
130 
137  void setCacheSubsetOfAttributes( const QgsAttributeList &attributes );
138 
147 
154  void setCacheAddedAttributes( bool cacheAddedAttributes );
155 
169  void setFullCache( bool fullCache );
170 
177  bool hasFullCache() const { return mFullCache; }
178 
188 
199 
203  inline QgsFeatureIterator getFeatures( const QString &expression )
204  {
205  return getFeatures( QgsFeatureRequest( expression ) );
206  }
207 
213  {
214  QgsFeature feature;
215  getFeatures( QgsFeatureRequest( fid ) ).nextFeature( feature );
216  return feature;
217  }
218 
223  {
224  return getFeatures( QgsFeatureRequest( fids ) );
225  }
226 
230  inline QgsFeatureIterator getFeatures( const QgsRectangle &rectangle )
231  {
232  return getFeatures( QgsFeatureRequest( rectangle ) );
233  }
234 
241  bool isFidCached( QgsFeatureId fid ) const;
242 
248 
256  bool featureAtId( QgsFeatureId featureId, QgsFeature &feature, bool skipCache = false );
257 
271  bool featureAtIdWithAllAttributes( QgsFeatureId featureId, QgsFeature &feature, bool skipCache = false );
272 
278  bool removeCachedFeature( QgsFeatureId fid );
279 
284 
289 
293  QgsFields fields() const;
294 
298  Qgis::WkbType wkbType() const;
299 
300 #ifdef SIP_RUN
301 
306  int __len__() const;
307  % MethodCode
308  sipRes = sipCpp->featureCount();
309  % End
310 
312  int __bool__() const;
313  % MethodCode
314  sipRes = true;
315  % End
316 #endif
317 
322  long long featureCount() const;
323 
324  protected:
325 
334  void requestCompleted( const QgsFeatureRequest &featureRequest, const QgsFeatureIds &fids );
335 
343  void featureRemoved( QgsFeatureId fid );
344 
355  bool checkInformationCovered( const QgsFeatureRequest &featureRequest );
356 
357 
358  signals:
359 
369  void progress( int i, bool &cancel ) SIP_SKIP;
370 
374  void finished();
375 
382 
387  void attributeValueChanged( QgsFeatureId fid, int field, const QVariant &value );
388 
397 
403  void invalidated();
404 
405  private slots:
406  void onAttributeValueChanged( QgsFeatureId fid, int field, const QVariant &value );
407  void onJoinAttributeValueChanged( QgsFeatureId fid, int field, const QVariant &value );
408  void featureDeleted( QgsFeatureId fid );
409  void onFeatureAdded( QgsFeatureId fid );
410  void attributeAdded( int field );
411  void attributeDeleted( int field );
412  void geometryChanged( QgsFeatureId fid, const QgsGeometry &geom );
413  void layerDeleted();
414  void invalidate();
415 
416  private:
417 
418  void connectJoinedLayers() const;
419 
420  inline void cacheFeature( QgsFeature &feat, bool allAttributesFetched )
421  {
422  QgsCachedFeature *cachedFeature = new QgsCachedFeature( feat, this, allAttributesFetched );
423  mCache.insert( feat.id(), cachedFeature );
424  if ( mCacheUnorderedKeys.find( feat.id() ) == mCacheUnorderedKeys.end() )
425  {
426  mCacheUnorderedKeys.insert( feat.id() );
427  mCacheOrderedKeys.emplace_back( feat.id() );
428  }
429  }
430 
431  QgsVectorLayer *mLayer = nullptr;
432  QCache< QgsFeatureId, QgsCachedFeature > mCache;
433 
434  // we need two containers here. One is used for efficient tracking of the IDs which have been added to the cache, the other
435  // is used to store the order of the incoming feature ids, so that we can correctly iterate through features in the original order.
436  // the ordered list alone is far too slow to handle this -- searching for existing items in a list is magnitudes slower than the unordered_set
437  std::unordered_set< QgsFeatureId > mCacheUnorderedKeys;
438  std::deque< QgsFeatureId > mCacheOrderedKeys;
439 
440  bool mCacheGeometry = true;
441  bool mFullCache = false;
442  QList<QgsAbstractCacheIndex *> mCacheIndices;
443 
444  QgsAttributeList mCachedAttributes;
445 
448  friend class QgsCachedFeature;
449 
458  bool canUseCacheForRequest( const QgsFeatureRequest &featureRequest, QgsFeatureIterator &it );
459 
460  friend class TestVectorLayerCache;
461 };
462 #endif // QgsVectorLayerCache_H
WkbType
The WKB type describes the number of dimensions a geometry has.
Definition: qgis.h:182
Abstract base class for cache indices.
Definition: qgscacheindex.h:32
Delivers features from the cache.
Uses another iterator as backend and writes features to the cache.
This class represents a coordinate reference system (CRS).
Wrapper for iterator of features from vector data provider or vector layer.
bool nextFeature(QgsFeature &f)
Fetch next feature and stores in f, returns true on success.
This class wraps a request for features to a vector layer (or directly its vector data provider).
The feature class encapsulates a single feature including its unique ID, geometry and a list of field...
Definition: qgsfeature.h:56
Q_GADGET QgsFeatureId id
Definition: qgsfeature.h:64
Container of fields for a vector layer.
Definition: qgsfields.h:45
A geometry is the spatial representation of a feature.
Definition: qgsgeometry.h:162
A rectangle specified with double values.
Definition: qgsrectangle.h:42
This class caches features of a given QgsVectorLayer.
bool isFidCached(QgsFeatureId fid) const
Check if a certain feature id is cached.
void setFullCache(bool fullCache)
This enables or disables full caching.
bool hasFullCache() const
Returns true if the cache is complete, ie it contains all features.
QgsFeatureIterator getFeatures(const QString &expression)
Query the layer for features matching a given expression.
void finished()
When filling the cache, this signal gets emitted once the cache is fully initialized.
void featureRemoved(QgsFeatureId fid)
Gets called, whenever a feature has been removed.
void setCacheAddedAttributes(bool cacheAddedAttributes)
If this is enabled, the subset of cached attributes will automatically be extended to also include ne...
void invalidated()
The cache has been invalidated and cleared.
void setCacheSize(int cacheSize)
Sets the maximum number of features to keep in the cache.
void setCacheSubsetOfAttributes(const QgsAttributeList &attributes)
Set the list (possibly a subset) of attributes to be cached.
QgsFeatureIterator getFeatures(const QgsRectangle &rectangle)
Query the layer for the features which intersect the specified rectangle.
void featureAdded(QgsFeatureId fid)
Emitted when a new feature has been added to the layer and this cache.
QgsFields fields() const
Returns the fields associated with features in the cache.
QgsFeatureIterator getFeatures(const QgsFeatureIds &fids)
Query the layer for the features with the given ids.
QgsFeature getFeature(QgsFeatureId fid)
Query the layer for the feature with the given id.
void cachedLayerDeleted()
Is emitted when the cached layer is deleted.
void requestCompleted(const QgsFeatureRequest &featureRequest, const QgsFeatureIds &fids)
Gets called, whenever the full list of feature ids for a certain request is known.
void attributeValueChanged(QgsFeatureId fid, int field, const QVariant &value)
Emitted when an attribute is changed.
bool removeCachedFeature(QgsFeatureId fid)
Removes the feature identified by fid from the cache if present.
void progress(int i, bool &cancel)
When filling the cache, this signal gets emitted periodically to notify about the progress and to be ...
QgsVectorLayer * layer()
Returns the layer to which this cache belongs.
long long featureCount() const
Returns the number of features contained in the source, or -1 if the feature count is unknown.
QgsCoordinateReferenceSystem sourceCrs() const
Returns the coordinate reference system for features in the cache.
bool checkInformationCovered(const QgsFeatureRequest &featureRequest)
Checks if the information required to complete the request is cached.
QgsFeatureIds cachedFeatureIds() const
Returns the set of feature IDs for features which are cached.
bool featureAtIdWithAllAttributes(QgsFeatureId featureId, QgsFeature &feature, bool skipCache=false)
Gets the feature at the given feature id with all attributes, if the cached feature already contains ...
bool cacheGeometry() const
Returns true if the cache will fetch and cache feature geometries.
Qgis::WkbType wkbType() const
Returns the geometry type for features in the cache.
int cacheSize()
Returns the maximum number of features this cache will hold.
QgsAttributeList cacheSubsetOfAttributes() const
Returns the list (possibly a subset) of cached attributes.
void addCacheIndex(QgsAbstractCacheIndex *cacheIndex)
Adds a QgsAbstractCacheIndex to this cache.
QgsVectorLayerCache(QgsVectorLayer *layer, int cacheSize, QObject *parent=nullptr)
void setCacheGeometry(bool cacheGeometry)
Enable or disable the caching of geometries.
QgsFeatureIterator getFeatures(const QgsFeatureRequest &featureRequest=QgsFeatureRequest())
Query this VectorLayerCache for features.
bool featureAtId(QgsFeatureId featureId, QgsFeature &feature, bool skipCache=false)
Gets the feature at the given feature id.
Represents a vector layer which manages a vector based data sets.
#define SIP_TRANSFERTHIS
Definition: qgis_sip.h:53
#define SIP_SKIP
Definition: qgis_sip.h:126
#define SIP_TRANSFER
Definition: qgis_sip.h:36
QSet< QgsFeatureId > QgsFeatureIds
Definition: qgsfeatureid.h:37
qint64 QgsFeatureId
64 bit feature ids negative numbers are used for uncommitted/newly added features
Definition: qgsfeatureid.h:28
QList< int > QgsAttributeList
Definition: qgsfield.h:27