Loading...
Searching...
No Matches
BitOps.H
Go to the documentation of this file.
1/*---------------------------------------------------------------------------*\
2 ========= |
3 \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
4 \\ / O peration |
5 \\ / A nd | www.openfoam.com
6 \\/ M anipulation |
7-------------------------------------------------------------------------------
8 Copyright (C) 2018-2025 OpenCFD Ltd.
9-------------------------------------------------------------------------------
10License
11 This file is part of OpenFOAM.
12
13 OpenFOAM is free software: you can redistribute it and/or modify it
14 under the terms of the GNU General Public License as published by
15 the Free Software Foundation, either version 3 of the License, or
16 (at your option) any later version.
17
18 OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
19 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
20 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
21 for more details.
22
23 You should have received a copy of the GNU General Public License
24 along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
25
26Namespace
27 Foam::BitOps
28
29Description
30 Various bit-wise operations and adaptor methods for containers
31 that are somewhat similar to bitSet (eg, boolList, labelHashSet).
32
33 The population count uses the Hamming weight
34 (http://en.wikipedia.org/wiki/Hamming_weight).
35
36Namespace
37 Foam::BitSetOps
38
39Description
40 Factory and other methods for bitSet.
41 Adaptor methods for other containers that are somewhat similar to
42 bitSet (eg, boolList, labelHashSet).
43
44\*---------------------------------------------------------------------------*/
45
46#ifndef Foam_BitOps_H
47#define Foam_BitOps_H
48
49#include "UList.H"
50#include "HashSet.H"
51#include "Ostream.H"
52#include <limits>
53
54// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
55
56namespace Foam
57{
58
59// Forward Declarations
60class bitSet;
61template<class T> class List;
62
63/*---------------------------------------------------------------------------*\
64 Namespace BitOps Declaration
65\*---------------------------------------------------------------------------*/
66
67namespace BitOps
68{
69
70// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
71
72//- Count number of 'true' entries.
73// \param val can be set to false to count the number of false values instead
74// For compatibility with bitSet::count()
75inline unsigned int count(const UList<bool>& bools, const bool val=true)
76{
77 return std::count(bools.begin(), bools.end(), val);
78}
79
80//- True if all entries are 'true' or if the list is empty.
81// For compatibility with bitSet::all()
82inline bool all(const UList<bool>& bools) { return bools.all(); }
84//- True if any entries are 'true'.
85// For compatibility with bitSet::any()
86inline bool any(const UList<bool>& bools) { return bools.any(); }
87
88//- True if no entries are 'true'.
89// For compatibility with bitSet::none()
90inline bool none(const UList<bool>& bools) { return bools.none(); }
91
92
93//- Set the listed locations (assign 'true').
94// Does auto-vivify for non-existent entries.
95//
96// For compatibility with bitSet::set(labelUList)
97void set(List<bool>& bools, const labelUList& locations);
98
99//- Set the specified range 'on' in a boolList.
100// For compatibility with bitSet::set(labelRange)
101void set(List<bool>& bools, const labelRange& range);
102
103//- Set the specified range in a labelHashSet.
104// For compatibility with bitSet::set(labelRange)
105void set(labelHashSet& hashset, const labelRange& range);
106
107//- Forward to bitSet::set(labelRange)
108void set(bitSet& bitset, const labelRange& range);
109
110
111//- Unset the listed locations (assign 'false').
112// No auto-vivify non-existent entries.
113//
114// For compatibility with bitSet::set(labelUList)
115void unset(List<bool>& bools, const labelUList& locations);
116
117//- Unset the specified range 'on' in a boolList.
118// For compatibility with bitSet::unset(labelRange)
119void unset(List<bool>& bools, const labelRange& range);
120
121//- Unset the specified range in a labelHashSet.
122// For compatibility with bitSet::unset(labelRange)
123void unset(labelHashSet& hashset, const labelRange& range);
124
125//- Forward to bitSet::unset(labelRange)
126void unset(bitSet& bitset, const labelRange& range);
127
128
129//- Construct a selection list of bools (all false) with the given pre-size,
130//- subsequently add specified locations as true,
131//- auto-vivify entries if needed.
132// Similar to bitSet construction from locations
133//
134// \return a List of bools
135List<bool> select(const label n, const labelUList& locations);
136
137//- Construct an auto-sized selection list of bools (all false),
138//- and populate the specified locations as true.
139// Similar to bitSet construction from locations
140//
141// \return a List of bools
142List<bool> select(const labelUList& locations);
143
144//- Forward to bitSet::count()
145unsigned int count(const bitSet& bitset, const bool on=true);
146
147
148//- Return the (sorted) values corresponding to 'true' entries.
149// Similar to bitSet::toc()
150//
151// \return a List of labels
152List<label> toc(const UList<bool>& bools);
153
154//- Return the (sorted) values corresponding to 'true' entries.
155// Similar to bitSet::sortedToc() and labelHashSet::sortedToc()
156//
157// \return a List of labels
158List<label> sortedToc(const UList<bool>& bools);
159
160
161//- Forward to bitSet::toc(), the sorted values of the 'on' entries.
162//
163// \return a List of labels
164List<label> toc(const bitSet& bitset);
165
166//- Forward to bitSet::sortedToc(), the sorted values of the 'on' entries.
167//
168// \return a List of labels
169List<label> sortedToc(const bitSet& bitset);
170
171
172//- Forward to labelHashSet::sortedToc(), the sorted values of the 'on' entries.
173//
174// \return a List of labels
175List<label> toc(const labelHashSet& hashset);
176
177//- Forward to labelHashSet::sortedToc(), the sorted values of the 'on' entries.
178//
179// \return a List of labels
180List<label> sortedToc(const labelHashSet& hashset);
181
182
183//- Count arbitrary number of bits (of an integral type)
184template<class UIntType>
185inline unsigned int bit_count(UIntType x)
186{
187 unsigned int n = 0u;
188
189 for (; x; ++n) { x &= (x-1); }
190
191 return n;
192}
193
194
195//- Count bits in a 32-bit value (Hamming weight method)
196template<>
197inline unsigned int bit_count(uint32_t x)
198{
199 x -= (x >> 1) & 0x55555555;
200 x = (x & 0x33333333) + ((x >> 2) & 0x33333333);
201
202 return ((((x + (x >> 4)) & 0x0F0F0F0F) * 0x01010101) >> 24);
203}
204
205
206//- Count bits in a 64-bit value (Hamming weight method)
207template<>
208inline unsigned int bit_count(uint64_t x)
209{
210 x -= (x >> 1) & 0x5555555555555555;
211 x = (x & 0x3333333333333333) + ((x >> 2) & 0x3333333333333333);
212
213 return unsigned
214 ((((x + (x >> 4)) & 0x0F0F0F0F0F0F0F0F) * 0x0101010101010101) >> 56);
215}
216
217
218//- Repeat a value of the given BitWidth into the destination output type.
219//
220// \note when BitWidth is 1, it is better to do directly.
221// \code
222// (val ? ~0u : 0u)
223// \endcode
224template<class UIntType, unsigned BitWidth>
225inline UIntType repeat_value(unsigned val)
226{
227 static_assert
228 (
229 BitWidth && std::numeric_limits<UIntType>::digits >= BitWidth,
230 "BitWidth too large for target output"
231 );
232
233 // How many fit into the target
234 const unsigned nrepeat = (std::numeric_limits<UIntType>::digits / BitWidth);
235
236 // Max value for a single element
237 const unsigned mask = ((1u << BitWidth) - 1);
238
239 // The first occurrence
240 UIntType fillval = ((val >= mask) ? mask : val);
241
242 // Repeated
243 for (unsigned i = 1; i < nrepeat; ++i)
244 {
245 fillval |= (fillval << BitWidth);
246 }
247
248 return fillval;
249}
250
251
252//- Print 0/1 bits in the (unsigned) integral type
253template<class UIntType>
254inline Ostream& print(Ostream& os, UIntType value, char off='0', char on='1')
255{
256 if (os.format() == IOstreamOption::BINARY)
257 {
258 // Perhaps not the most sensible, but the only thing we currently have.
259 os << label(value);
260 }
261 else
262 {
263 // Starting from most significant bit - makes for easy reading.
264 for
265 (
266 unsigned test = (1u << (std::numeric_limits<UIntType>::digits-1));
267 test;
268 test >>= 1u
270 {
271 os << ((value & test) ? on : off);
272 }
273 }
274
275 return os;
276}
277
278
279//- An (unsigned) integral type adapter, for output of bit values
280template<class UIntType>
281struct bitInfo
282{
283 typedef UIntType value_type;
285
286 //- Null constructible as zero
287 constexpr bitInfo() noexcept : value(0) {}
288
289 //- Value construct
290 explicit bitInfo(UIntType val) noexcept : value(val) {}
291
292 //- Conversion to base type
293 operator UIntType () const noexcept { return value; }
294
295 //- Conversion to base type
296 operator UIntType& () noexcept { return value; }
297};
298
299} // End namespace BitOps
300
301
302/*---------------------------------------------------------------------------*\
303 Namespace BitSetOps Declaration
304\*---------------------------------------------------------------------------*/
305
306namespace BitSetOps
307{
308
309// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
310
311//- Create a bitSet with length n with the specified \a on locations.
312// The resulting bitSet is guaranteed to have \b exactly the specified length,
313// any values or positions larger than n-1 are silently ignored.
314//
315// \param n the size of the output bitSet
316// \param locations the list of positions corresponding to an \a on bit.
317// \param on the value for on. Set as false to invert the logic.
318//
319// \return a bitset
321(
322 const label n,
323 const labelHashSet& locations,
324 const bool on = true
325);
326
327
328//- Create a bitSet with length n with the specified \a on locations.
329// The resulting bitSet is guaranteed to have \b exactly the specified length,
330// any values or positions larger than n-1 are silently ignored.
331//
332// \param n the size of the output bitSet
333// \param locations the list of positions corresponding to an \a on bit.
334// \param on the value for on. Set as false to invert the logic.
335//
336// \return a bitset
338(
339 const label n,
340 const labelUList& locations,
341 const bool on = true
342);
343
344
345//- Create a bitSet with length n with the specified \a on locations
346//- when the list values are equal to the select value.
347//
348// The resulting bitSet is guaranteed to have \b exactly the specified length,
349// any values or positions larger than n-1 are silently ignored.
350//
351// \param n the size of the output bitSet
352// \param select the value to select as 'on'
353// \param values the values to scan for 'select'
354// \param on the value for on. Set as false to invert the logic.
355//
356// \return a bitset
358(
359 const label n,
360 const label select,
361 const labelUList& values,
362 const bool on = true
363);
364
365} // End namespace BitSetOps
366
368// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
369
370
371//- Print 0/1 bits of an (unsigned) integral type via an adapter
372template<class UIntType>
374{
375 BitOps::print(os, info.value);
376 return os;
377}
378
379
380// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
381
382} // End namespace Foam
383
384// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
385
386#endif
387
388// ************************************************************************* //
scalar range
label n
A 1D array of objects of type <T>, where the size of the vector is known and used for subscript bound...
Definition List.H:72
An Ostream is an abstract base class for all output systems (streams, files, token lists,...
Definition Ostream.H:59
A 1D vector of objects of type <T>, where the size of the vector is known and can be used for subscri...
Definition UList.H:89
bool any() const
True if any entries are 'true'.
Definition UList.H:821
iterator begin() noexcept
Return an iterator to begin traversing the UList.
Definition UListI.H:410
bool none() const
True if no entries are 'true'.
Definition UList.H:836
iterator end() noexcept
Return an iterator to end traversing the UList.
Definition UListI.H:454
bool all() const
True if all entries are 'true' or if the list is empty.
Definition UList.H:806
A bitSet stores bits (elements with only two states) in packed internal format and supports a variety...
Definition bitSet.H:61
A range or interval of labels defined by a start and a size.
Definition labelRange.H:66
OBJstream os(runTime.globalPath()/outputName)
Various bit-wise operations and adaptor methods for containers that are somewhat similar to bitSet (e...
void set(List< bool > &bools, const labelUList &locations)
Set the listed locations (assign 'true').
Definition BitOps.C:35
List< bool > select(const label n, const labelUList &locations)
Construct a selection list of bools (all false) with the given pre-size, subsequently add specified l...
Definition BitOps.C:139
void unset(List< bool > &bools, const labelUList &locations)
Unset the listed locations (assign 'false').
Definition BitOps.C:104
List< label > toc(const UList< bool > &bools)
Return the (sorted) values corresponding to 'true' entries.
Definition BitOps.C:163
bool any(const UList< bool > &bools)
True if any entries are 'true'.
Definition BitOps.H:90
unsigned int count(const UList< bool > &bools, const bool val=true)
Count number of 'true' entries.
Definition BitOps.H:73
bool all(const UList< bool > &bools)
True if all entries are 'true' or if the list is empty.
Definition BitOps.H:83
unsigned int bit_count(UIntType x)
Count arbitrary number of bits (of an integral type).
Definition BitOps.H:242
List< label > sortedToc(const UList< bool > &bools)
Return the (sorted) values corresponding to 'true' entries.
Definition BitOps.C:200
Ostream & print(Ostream &os, UIntType value, char off='0', char on='1')
Print 0/1 bits in the (unsigned) integral type.
Definition BitOps.H:320
bool none(const UList< bool > &bools)
True if no entries are 'true'.
Definition BitOps.H:97
UIntType repeat_value(unsigned val)
Repeat a value of the given BitWidth into the destination output type.
Definition BitOps.H:289
Factory and other methods for bitSet. Adaptor methods for other containers that are somewhat similar ...
bitSet create(const label n, const labelHashSet &locations, const bool on=true)
Create a bitSet with length n with the specified on locations.
Definition BitOps.C:233
Namespace for OpenFOAM.
HashSet< label, Hash< label > > labelHashSet
A HashSet of labels, uses label hasher.
Definition HashSet.H:85
Ostream & operator<<(Ostream &, const boundaryPatch &p)
Write boundaryPatch as dictionary entries (without surrounding braces).
const direction noexcept
Definition scalarImpl.H:265
UList< label > labelUList
A UList of labels.
Definition UList.H:75
An (unsigned) integral type adapter, for output of bit values.
Definition BitOps.H:350
UIntType value_type
Definition BitOps.H:351
constexpr bitInfo() noexcept
Null constructible as zero.
Definition BitOps.H:357
bitInfo(UIntType val) noexcept
Value construct.
Definition BitOps.H:362
value_type value
Definition BitOps.H:352