JKQTPlotter trunk/v5.0.0
an extensive Qt5+Qt6 Plotter framework (including a feature-richt plotter widget, a speed-optimized, but limited variant and a LaTeX equation renderer!), written fully in C/C++ and without external dependencies
Loading...
Searching...
No Matches
jkqtpconcurrencytools.h
1/*
2 Copyright (c) 2008-2023 Jan W. Krieger (<jan@jkrieger.de>)
3
4 last modification: $LastChangedDate$ (revision $Rev$)
5
6 This software is free software: you can redistribute it and/or modify
7 it under the terms of the GNU Lesser General Public License (LGPL) as published by
8 the Free Software Foundation, either version 2.1 of the License, or
9 (at your option) any later version.
10
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU Lesser General Public License (LGPL) for more details.
15
16 You should have received a copy of the GNU Lesser General Public License (LGPL)
17 along with this program. If not, see <http://www.gnu.org/licenses/>.
18*/
19
20
21
22
23
24#ifndef JKQTPCONCURRENCYTOOLS_H
25#define JKQTPCONCURRENCYTOOLS_H
26
27#include "jkqtcommon/jkqtcommon_imexport.h"
28#include <QReadWriteLock>
29#include <QReadLocker>
30#include <QWriteLocker>
31#include <mutex>
32
33/** \brief template class that wraps any datatype and combines it with a mutex, exposes the lock()/unlock()
34 * interface, so access to the contained data can be synchronized
35 * \ingroup jkqtptools_concurrency
36 *
37 *
38 */
39template <class T>
41public:
42 /** \brief Mutex used by this temmplate */
43 typedef QReadWriteLock MutexType;
44
45 /** \brief type of AdoptLock tag, which is used in ReadLocker and WriteLocker to adopt a pre-locked JKQTPSynchronized<T> */
46 struct AdoptLockType { explicit AdoptLockType() = default; };
47 /** \brief tag, which is used in ReadLocker and WriteLocker to adopt a pre-locked JKQTPSynchronized<T> */
48 static constexpr AdoptLockType AdoptLock { };
49
50 /** \brief type of a lock_guard for a JKQTPSynchronized<T> for reading */
52 {
53 public:
54 inline ReadLocker(const JKQTPSynchronized<T> &sync) noexcept: m_sync(sync) { m_sync.lockForRead(); };
55 inline ReadLocker(const JKQTPSynchronized<T> &sync, AdoptLockType) noexcept : m_sync(sync) { };
56 inline ~ReadLocker() { m_sync.unlock(); }
57 private:
59 const JKQTPSynchronized<T> &m_sync;
60 };
61
62 /** \brief type of a lock_guard for a JKQTPSynchronized<T> for writing */
64 {
65 public:
66 inline WriteLocker(JKQTPSynchronized<T> &sync) noexcept: m_sync(sync) { m_sync.lockForWrite(); };
67 inline WriteLocker(JKQTPSynchronized<T> &sync, AdoptLockType) noexcept : m_sync(sync) { };
68 inline ~WriteLocker() { m_sync.unlock(); }
69 private:
72 };
73
74 /** \brief type of a lock_guard for a JKQTPSynchronized<T> for writing */
76 /** \brief contained data type T */
77 typedef T data_type;
78 /** \brief default constructor, the internal data is default-initialized */
80 /** \brief initializing constructor, the internal data is initialized with \a d */
81 inline JKQTPSynchronized(const T& d): m_data(d) {}
82 /** \brief initializing constructor, the internal data is initialized with \a d */
83 inline JKQTPSynchronized(T&& d): m_data(std::forward<T>(d)) {}
84 /** \brief locks \a other and copies its contents to this new class */
86 Locker lock(other);
87 m_data=other.m_data;
88 }
89 /** \brief locks \a other and moves its contents to this new class. The mutex in \a other is NOT moved! */
91 Locker lock(other);
92 m_data=std::move(other.m_data);
93 }
94
95 /** \brief locks the internal mutex for writing, until unlock() is called
96 *
97 * \note Use WriteLocker or Locker instances to actually lock, using a RAII-idiom, as this is safer than doing this by hand!
98 */
99 inline void lock() const {
100 lockForWrite();
101 }
102 /** \brief locks the internal mutex for writing, until unlock() is called
103 *
104 * \note Use WriteLocker or Locker instances to actually lock, using a RAII-idiom, as this is safer than doing this by hand!
105 */
106 inline void lockForWrite() const {
107 m_mutex.lockForWrite();
108 }
109 /** \brief locks the internal mutex for writing, until unlock() is called
110 *
111 * \note Use WriteLocker or Locker instances to actually lock, using a RAII-idiom, as this is safer than doing this by hand!
112 */
113 inline void lockForRead() const {
114 m_mutex.lockForRead();
115 }
116 /** \brief unlocks the internal mutex from a previous lock(), lockForWrite() or lockForRead() call
117 *
118 * \note Use Locker instances to actually lock, using a RAII-idiom, as this is safer than doing this by hand!
119 */
120 inline void unlock() const {
121 m_mutex.unlock();
122 }
123 /** \brief assign a value to the internal data storage, <b>not thread-safe.</b>
124 *
125 * \note You need to lock this object before calling this function.
126 */
127 inline void set(const T& d) {
128 m_data=d;
129 }
130 /** \brief assign a value to the internal data storage, <b>not thread-safe</b>.
131 *
132 * \note You need to lock this object before calling this function.
133 */
134 inline void set(T&& d) {
135 m_data=std::forward<T>(d);
136 }
137 /** \brief assign a value to the internal data storage, <b>thread-safe</b>.
138 */
139 inline void set_safe(const T& d) {
140 Locker lck(m_mutex);
141 m_data=d;
142 }
143 /** \brief assign a value to the internal data storage, \b thread-safe.
144 */
145 inline void set_safe(T&& d) {
146 Locker lck(m_mutex);
147 m_data=std::forward<T>(d);
148 }
149 /** \brief returns the internal data as a mutable reference, <b>not thread-safe</b>.
150 *
151 * \note You need to lock this object before calling this function.
152 */
153 inline T& get() {
154 return m_data;
155 }
156 /** \brief returns the internal data as a mutable reference, <b>not thread-safe</b>.
157 *
158 * \note You need to lock this object before calling this function.
159 */
160 inline const T& get() const {
161 return m_data;
162 }
163 /** \brief gives access to the internal data, <b>not thread-safe</b>.
164 *
165 * \note You need to lock this object before calling this function.
166 */
167 inline const T* operator->() const {
168 return &m_data;
169 }
170 /** \brief gives access to the internal data, <b>not thread-safe</b>.
171 *
172 * \note You need to lock this object before calling this function.
173 */
174 inline T* operator->() {
175 return &m_data;
176 }
177 /** \brief returns the value in the internal data storage, <b>thread-safe</b>.
178 */
179 inline T get_safe() const {
180 ReadLocker lck(this);
181 return m_data;
182 }
183
184private:
187
188};
189
190#endif // JKQTPCONCURRENCYTOOLS_H
type of a lock_guard for a JKQTPSynchronized<T> for reading
Definition jkqtpconcurrencytools.h:52
ReadLocker(const JKQTPSynchronized< T > &sync, AdoptLockType) noexcept
Definition jkqtpconcurrencytools.h:55
ReadLocker(const JKQTPSynchronized< T > &sync) noexcept
Definition jkqtpconcurrencytools.h:54
~ReadLocker()
Definition jkqtpconcurrencytools.h:56
Q_DISABLE_COPY(ReadLocker) const JKQTPSynchronized< T > &m_sync
type of a lock_guard for a JKQTPSynchronized<T> for writing
Definition jkqtpconcurrencytools.h:64
WriteLocker(JKQTPSynchronized< T > &sync, AdoptLockType) noexcept
Definition jkqtpconcurrencytools.h:67
~WriteLocker()
Definition jkqtpconcurrencytools.h:68
WriteLocker(JKQTPSynchronized< T > &sync) noexcept
Definition jkqtpconcurrencytools.h:66
Q_DISABLE_COPY(WriteLocker) JKQTPSynchronized< T > &m_sync
template class that wraps any datatype and combines it with a mutex, exposes the lock()/unlock() inte...
Definition jkqtpconcurrencytools.h:40
JKQTPSynchronized(const JKQTPSynchronized< T > &other)
locks other and copies its contents to this new class
Definition jkqtpconcurrencytools.h:85
MutexType m_mutex
Definition jkqtpconcurrencytools.h:186
JKQTPSynchronized(JKQTPSynchronized< T > &&other)
locks other and moves its contents to this new class. The mutex in other is NOT moved!
Definition jkqtpconcurrencytools.h:90
void set(T &&d)
assign a value to the internal data storage, not thread-safe.
Definition jkqtpconcurrencytools.h:134
JKQTPSynchronized(const T &d)
initializing constructor, the internal data is initialized with d
Definition jkqtpconcurrencytools.h:81
const T * operator->() const
gives access to the internal data, not thread-safe.
Definition jkqtpconcurrencytools.h:167
void lockForRead() const
locks the internal mutex for writing, until unlock() is called
Definition jkqtpconcurrencytools.h:113
T * operator->()
gives access to the internal data, not thread-safe.
Definition jkqtpconcurrencytools.h:174
JKQTPSynchronized()
default constructor, the internal data is default-initialized
Definition jkqtpconcurrencytools.h:79
T m_data
Definition jkqtpconcurrencytools.h:185
const T & get() const
returns the internal data as a mutable reference, not thread-safe.
Definition jkqtpconcurrencytools.h:160
QReadWriteLock MutexType
Mutex used by this temmplate.
Definition jkqtpconcurrencytools.h:43
void lockForWrite() const
locks the internal mutex for writing, until unlock() is called
Definition jkqtpconcurrencytools.h:106
T & get()
returns the internal data as a mutable reference, not thread-safe.
Definition jkqtpconcurrencytools.h:153
T data_type
contained data type T
Definition jkqtpconcurrencytools.h:77
JKQTPSynchronized(T &&d)
initializing constructor, the internal data is initialized with d
Definition jkqtpconcurrencytools.h:83
void set_safe(T &&d)
assign a value to the internal data storage, thread-safe.
Definition jkqtpconcurrencytools.h:145
void set(const T &d)
assign a value to the internal data storage, not thread-safe.
Definition jkqtpconcurrencytools.h:127
static constexpr AdoptLockType AdoptLock
tag, which is used in ReadLocker and WriteLocker to adopt a pre-locked JKQTPSynchronized<T>
Definition jkqtpconcurrencytools.h:48
T get_safe() const
returns the value in the internal data storage, thread-safe.
Definition jkqtpconcurrencytools.h:179
void unlock() const
unlocks the internal mutex from a previous lock(), lockForWrite() or lockForRead() call
Definition jkqtpconcurrencytools.h:120
JKQTPSynchronized< T >::WriteLocker Locker
type of a lock_guard for a JKQTPSynchronized<T> for writing
Definition jkqtpconcurrencytools.h:75
void set_safe(const T &d)
assign a value to the internal data storage, thread-safe.
Definition jkqtpconcurrencytools.h:139
void lock() const
locks the internal mutex for writing, until unlock() is called
Definition jkqtpconcurrencytools.h:99
type of AdoptLock tag, which is used in ReadLocker and WriteLocker to adopt a pre-locked JKQTPSynchro...
Definition jkqtpconcurrencytools.h:46