diff options
author | Sven Gothel <[email protected]> | 2020-06-24 22:54:04 +0200 |
---|---|---|
committer | Sven Gothel <[email protected]> | 2020-06-24 22:54:04 +0200 |
commit | 3cf7e59c2dbd20e1e781d90d9308a56fd449e040 (patch) | |
tree | ec217f2571dbb2a4c71930089ac11b8cad0bb77c | |
parent | 766ef519b8ada7711f059ea28f3073f50934b3f0 (diff) |
*Ringbuffer: Add 'drop(int count)' method, dropping max count oldest elements
-rw-r--r-- | api/direct_bt/LFRingbuffer.hpp | 23 | ||||
-rw-r--r-- | api/direct_bt/Ringbuffer.hpp | 10 |
2 files changed, 33 insertions, 0 deletions
diff --git a/api/direct_bt/LFRingbuffer.hpp b/api/direct_bt/LFRingbuffer.hpp index 14447664..ebaaa6a0 100644 --- a/api/direct_bt/LFRingbuffer.hpp +++ b/api/direct_bt/LFRingbuffer.hpp @@ -34,6 +34,7 @@ #include <mutex> #include <condition_variable> #include <chrono> +#include <algorithm> #include "BasicTypes.hpp" @@ -188,6 +189,24 @@ template <typename T, std::nullptr_t nullelem> class LFRingbuffer : public Ringb return r; } + int dropImpl (const int count) { + // locks ringbuffer completely (read/write), hence no need for local copy nor wait/sync etc + std::unique_lock<std::mutex> lockMultiRead(syncMultiRead); // RAII-style acquire and relinquish via destructor + std::unique_lock<std::mutex> lockMultiWrite(syncMultiWrite); // ditto + + const int dropCount = std::min(count, size.load()); + if( 0 == dropCount ) { + return 0; + } + for(int i=0; i<dropCount; i++) { + readPos = (readPos + 1) % capacityPlusOne; + // T r = array[localReadPos]; + array[readPos] = nullelem; + size--; + } + return dropCount; + } + bool putImpl(const T &e, const bool sameRef, const bool blocking, const int timeoutMS) /* throws InterruptedException */ { std::unique_lock<std::mutex> lockMultiWrite(syncMultiWrite); // RAII-style acquire and relinquish via destructor @@ -373,6 +392,10 @@ template <typename T, std::nullptr_t nullelem> class LFRingbuffer : public Ringb return getImpl(true, true, timeoutMS); } + int drop(const int count) override { + return dropImpl(count); + } + bool put(const T & e) override { return putImpl(e, false, false, 0); } diff --git a/api/direct_bt/Ringbuffer.hpp b/api/direct_bt/Ringbuffer.hpp index 692dbdf0..4a4c525c 100644 --- a/api/direct_bt/Ringbuffer.hpp +++ b/api/direct_bt/Ringbuffer.hpp @@ -137,6 +137,16 @@ template <class T> class Ringbuffer { virtual T peekBlocking(const int timeoutMS=0) /* throws InterruptedException */ = 0; /** + * Drops up to {@code count} oldest enqueued elements. + * <p> + * Method is non blocking and returns immediately;. + * </p> + * @param count maximum number of elements to drop from ringbuffer. + * @return actual number of dropped elements. + */ + virtual int drop(const int count) = 0; + + /** * Enqueues the given element. * <p> * Returns true if successful, otherwise false in case buffer is full. |