momo  3.12
unordered_set.h
Go to the documentation of this file.
1 /**********************************************************\
2 
3  This file is part of the
4  https://github.com/morzhovets/momo
5  project, distributed under the MIT License. See
6  https://github.com/morzhovets/momo/blob/branch_cpp11/LICENSE
7  for details.
8 
9  momo/stdish/unordered_set.h
10 
11  namespace momo::stdish:
12  class unordered_set_adaptor
13  class unordered_set
14  class unordered_set_open
15 
16 \**********************************************************/
17 
18 #ifndef MOMO_INCLUDE_GUARD_STDISH_UNORDERED_SET
19 #define MOMO_INCLUDE_GUARD_STDISH_UNORDERED_SET
20 
21 #include "set_map_utility.h"
22 #include MOMO_PARENT_HEADER(HashSet)
23 
24 namespace momo
25 {
26 
27 namespace stdish
28 {
29 
30 template<typename THashSet>
32 {
33 private:
34  typedef THashSet HashSet;
35  typedef typename HashSet::HashTraits HashTraits;
36  typedef typename HashSet::MemManager MemManager;
37 
38 public:
39  typedef typename HashSet::Key key_type;
40  typedef typename HashTraits::Hasher hasher;
41  typedef typename HashTraits::EqualComparer key_equal;
42 
43  typedef HashSet nested_container_type;
44 
45  typedef size_t size_type;
46  typedef ptrdiff_t difference_type;
47 
49  typedef typename std::allocator_traits<typename MemManager::ByteAllocator>
50  ::template rebind_alloc<value_type> allocator_type;
51 
53  typedef typename HashSet::Iterator iterator;
54 
55  //typedef typename iterator::Reference reference;
58 
59  //typedef typename iterator::Pointer pointer;
60  typedef value_type* pointer;
62  //typedef typename std::allocator_traits<allocator_type>::pointer pointer;
63  //typedef typename std::allocator_traits<allocator_type>::const_pointer const_pointer;
64 
67 
70 
71 private:
72  template<typename KeyArg>
73  struct IsValidKeyArg : public HashTraits::template IsValidKeyArg<KeyArg>
74  {
75  };
76 
77  struct NodeTypeProxy : private node_type
78  {
79  typedef node_type NodeType;
80  MOMO_DECLARE_PROXY_FUNCTION(NodeType, GetExtractedItem)
81  };
82 
83 public:
85  {
86  }
87 
88  explicit unordered_set_adaptor(const allocator_type& alloc)
89  : mHashSet(HashTraits(), MemManager(alloc))
90  {
91  }
92 
93  explicit unordered_set_adaptor(size_type bucketCount, const allocator_type& alloc = allocator_type())
94  : mHashSet(HashTraits(bucketCount), MemManager(alloc))
95  {
96  }
97 
98  unordered_set_adaptor(size_type bucketCount, const hasher& hashFunc,
99  const allocator_type& alloc = allocator_type())
100  : mHashSet(HashTraits(bucketCount, hashFunc), MemManager(alloc))
101  {
102  }
103 
104  unordered_set_adaptor(size_type bucketCount, const hasher& hashFunc, const key_equal& equalComp,
105  const allocator_type& alloc = allocator_type())
106  : mHashSet(HashTraits(bucketCount, hashFunc, equalComp), MemManager(alloc))
107  {
108  }
109 
110  template<typename Iterator>
111  unordered_set_adaptor(Iterator first, Iterator last)
112  {
113  insert(first, last);
114  }
115 
116  template<typename Iterator>
117  unordered_set_adaptor(Iterator first, Iterator last, size_type bucketCount,
118  const allocator_type& alloc = allocator_type())
119  : unordered_set_adaptor(bucketCount, alloc)
120  {
121  insert(first, last);
122  }
123 
124  template<typename Iterator>
125  unordered_set_adaptor(Iterator first, Iterator last, size_type bucketCount, const hasher& hashFunc,
126  const allocator_type& alloc = allocator_type())
127  : unordered_set_adaptor(bucketCount, hashFunc, alloc)
128  {
129  insert(first, last);
130  }
131 
132  template<typename Iterator>
133  unordered_set_adaptor(Iterator first, Iterator last, size_type bucketCount, const hasher& hashFunc,
134  const key_equal& equalComp, const allocator_type& alloc = allocator_type())
135  : unordered_set_adaptor(bucketCount, hashFunc, equalComp, alloc)
136  {
137  insert(first, last);
138  }
139 
140  unordered_set_adaptor(std::initializer_list<value_type> values)
141  : mHashSet(values)
142  {
143  }
144 
145  unordered_set_adaptor(std::initializer_list<value_type> values, size_type bucketCount,
146  const allocator_type& alloc = allocator_type())
147  : mHashSet(values, HashTraits(bucketCount), MemManager(alloc))
148  {
149  }
150 
151  unordered_set_adaptor(std::initializer_list<value_type> values, size_type bucketCount,
152  const hasher& hashFunc, const allocator_type& alloc = allocator_type())
153  : mHashSet(values, HashTraits(bucketCount, hashFunc), MemManager(alloc))
154  {
155  }
156 
157  unordered_set_adaptor(std::initializer_list<value_type> values, size_type bucketCount,
158  const hasher& hashFunc, const key_equal& equalComp, const allocator_type& alloc = allocator_type())
159  : mHashSet(values, HashTraits(bucketCount, hashFunc, equalComp), MemManager(alloc))
160  {
161  }
162 
163 #ifdef MOMO_HAS_CONTAINERS_RANGES
164  template<std::ranges::input_range Range>
165  requires std::convertible_to<std::ranges::range_reference_t<Range>, value_type>
166  unordered_set_adaptor(std::from_range_t, Range&& values)
167  {
168  insert_range(std::forward<Range>(values));
169  }
170 
171  template<std::ranges::input_range Range>
172  requires std::convertible_to<std::ranges::range_reference_t<Range>, value_type>
173  unordered_set_adaptor(std::from_range_t, Range&& values, size_type bucketCount,
174  const allocator_type& alloc = allocator_type())
175  : unordered_set_adaptor(bucketCount, alloc)
176  {
177  insert_range(std::forward<Range>(values));
178  }
179 
180  template<std::ranges::input_range Range>
181  requires std::convertible_to<std::ranges::range_reference_t<Range>, value_type>
182  unordered_set_adaptor(std::from_range_t, Range&& values, size_type bucketCount,
183  const hasher& hashFunc, const allocator_type& alloc = allocator_type())
184  : unordered_set_adaptor(bucketCount, hashFunc, alloc)
185  {
186  insert_range(std::forward<Range>(values));
187  }
188 
189  template<std::ranges::input_range Range>
190  requires std::convertible_to<std::ranges::range_reference_t<Range>, value_type>
191  unordered_set_adaptor(std::from_range_t, Range&& values, size_type bucketCount,
192  const hasher& hashFunc, const key_equal& equalComp, const allocator_type& alloc = allocator_type())
193  : unordered_set_adaptor(bucketCount, hashFunc, equalComp, alloc)
194  {
195  insert_range(std::forward<Range>(values));
196  }
197 #endif // MOMO_HAS_CONTAINERS_RANGES
198 
200  : unordered_set_adaptor(std::move(right), right.get_allocator())
201  {
202  }
203 
205  : mHashSet(right.mHashSet.GetHashTraits(), MemManager(alloc))
206  {
207  if (right.get_allocator() == alloc)
208  {
209  mHashSet.Swap(right.mHashSet);
210  }
211  else
212  {
213  mHashSet.MergeFrom(right.mHashSet);
214  right.clear();
215  }
216  }
217 
219  : mHashSet(right.mHashSet)
220  {
221  }
222 
224  : mHashSet(right.mHashSet, MemManager(alloc))
225  {
226  }
227 
229 
232  {
233  return momo::internal::ContainerAssignerStd::Move(std::move(right), *this);
234  }
235 
237  {
238  return momo::internal::ContainerAssignerStd::Copy(right, *this);
239  }
240 
241  unordered_set_adaptor& operator=(std::initializer_list<value_type> values)
242  {
243  mHashSet = HashSet(values, mHashSet.GetHashTraits(), MemManager(get_allocator()));
244  return *this;
245  }
246 
247  void swap(unordered_set_adaptor& right) noexcept
248  {
250  }
251 
252  friend void swap(unordered_set_adaptor& left, unordered_set_adaptor& right) noexcept
253  {
254  left.swap(right);
255  }
256 
258  {
259  return mHashSet;
260  }
261 
263  {
264  return mHashSet;
265  }
266 
267  const_iterator begin() const noexcept
268  {
269  return mHashSet.GetBegin();
270  }
271 
272  //iterator begin() noexcept
273 
274  const_iterator end() const noexcept
275  {
276  return mHashSet.GetEnd();
277  }
278 
279  //iterator end() noexcept
280 
281  const_iterator cbegin() const noexcept
282  {
283  return begin();
284  }
285 
286  const_iterator cend() const noexcept
287  {
288  return end();
289  }
290 
291  float max_load_factor() const noexcept
292  {
293  return mHashSet.GetHashTraits().GetMaxLoadFactor(HashSet::bucketMaxItemCount);
294  }
295 
296  void max_load_factor(float maxLoadFactor)
297  {
298  if (maxLoadFactor == max_load_factor())
299  return;
300  if (maxLoadFactor <= 0.0 || maxLoadFactor > static_cast<float>(HashSet::bucketMaxItemCount))
301  MOMO_THROW(std::out_of_range("invalid load factor"));
302  HashTraits hashTraits(mHashSet.GetHashTraits(), maxLoadFactor);
303  HashSet hashSet(hashTraits, MemManager(get_allocator()));
304  hashSet.Reserve(size());
305  hashSet.Insert(begin(), end());
306  mHashSet = std::move(hashSet);
307  }
308 
310  {
311  return mHashSet.GetHashTraits().GetHasher();
312  }
313 
315  {
316  return mHashSet.GetHashTraits().GetEqualComparer();
317  }
318 
319  allocator_type get_allocator() const noexcept
320  {
321  return allocator_type(mHashSet.GetMemManager().GetByteAllocator());
322  }
323 
324  size_type max_size() const noexcept
325  {
326  return std::allocator_traits<allocator_type>::max_size(get_allocator());
327  }
328 
329  size_type size() const noexcept
330  {
331  return mHashSet.GetCount();
332  }
333 
334  MOMO_NODISCARD bool empty() const noexcept
335  {
336  return mHashSet.IsEmpty();
337  }
338 
339  void clear() noexcept
340  {
341  mHashSet.Clear();
342  }
343 
344  void rehash(size_type bucketCount)
345  {
346  bucketCount = momo::internal::UIntMath<>::Max(bucketCount, 2);
347  size_t logBucketCount = momo::internal::UIntMath<>::Log2(bucketCount - 1) + 1;
348  bucketCount = size_t{1} << logBucketCount;
349  reserve(mHashSet.GetHashTraits().CalcCapacity(bucketCount, HashSet::bucketMaxItemCount));
350  }
351 
353  {
354  mHashSet.Reserve(count);
355  }
356 
358  {
359  return mHashSet.Find(key);
360  }
361 
362  //iterator find(const key_type& key)
363 
364  template<typename KeyArg>
366  const_iterator> find(const KeyArg& key) const
367  {
368  return mHashSet.Find(key);
369  }
370 
371  //template<typename KeyArg>
372  //momo::internal::EnableIf<IsValidKeyArg<KeyArg>::value,
373  //iterator> find(const KeyArg& key)
374 
376  {
377  return contains(key) ? 1 : 0;
378  }
379 
380  template<typename KeyArg>
382  size_type> count(const KeyArg& key) const
383  {
384  return contains(key) ? 1 : 0;
385  }
386 
387  MOMO_FORCEINLINE bool contains(const key_type& key) const
388  {
389  return mHashSet.ContainsKey(key);
390  }
391 
392  template<typename KeyArg>
394  bool> contains(const KeyArg& key) const
395  {
396  return mHashSet.ContainsKey(key);
397  }
398 
399  MOMO_FORCEINLINE std::pair<const_iterator, const_iterator> equal_range(
400  const key_type& key) const
401  {
402  return { find(key), end() };
403  }
404 
405  //std::pair<iterator, iterator> equal_range(const key_type& key)
406 
407  template<typename KeyArg>
409  std::pair<const_iterator, const_iterator>> equal_range(const KeyArg& key) const
410  {
411  return { find(key), end() };
412  }
413 
414  //template<typename KeyArg>
415  //momo::internal::EnableIf<IsValidKeyArg<KeyArg>::value,
416  //std::pair<iterator, iterator>> equal_range(const KeyArg& key)
417 
418  std::pair<iterator, bool> insert(value_type&& value)
419  {
420  typename HashSet::InsertResult res = mHashSet.Insert(std::move(value));
421  return { res.position, res.inserted };
422  }
423 
425  {
426  if MOMO_CONSTEXPR_IF (HashTraits::useHintIterators)
427  return mHashSet.Add(hint, std::move(value));
428  else
429  return insert(std::move(value)).first;
430  }
431 
432  std::pair<iterator, bool> insert(const value_type& value)
433  {
434  typename HashSet::InsertResult res = mHashSet.Insert(value);
435  return { res.position, res.inserted };
436  }
437 
439  {
440  if MOMO_CONSTEXPR_IF (HashTraits::useHintIterators)
441  return mHashSet.Add(hint, value);
442  else
443  return insert(value).first;
444  }
445 
447  {
448  if (node.empty())
449  return { end(), false, node_type() };
450  typename HashSet::InsertResult res = mHashSet.Insert(
451  std::move(NodeTypeProxy::GetExtractedItem(node)));
452  return { res.position, res.inserted, res.inserted ? node_type() : std::move(node) };
453  }
454 
456  {
457  if MOMO_CONSTEXPR_IF (HashTraits::useHintIterators)
458  {
459  if (node.empty())
460  return end();
461  return mHashSet.Add(hint, std::move(NodeTypeProxy::GetExtractedItem(node)));
462  }
463  else
464  {
465  return insert(std::move(node)).position;
466  }
467  }
468 
469  template<typename Iterator>
470  void insert(Iterator first, Iterator last)
471  {
472  pvInsertRange(first, last);
473  }
474 
475  void insert(std::initializer_list<value_type> values)
476  {
477  mHashSet.Insert(values);
478  }
479 
480 #ifdef MOMO_HAS_CONTAINERS_RANGES
481  template<std::ranges::input_range Range>
482  requires std::convertible_to<std::ranges::range_reference_t<Range>, value_type>
483  void insert_range(Range&& values)
484  {
485  pvInsertRange(std::ranges::begin(values), std::ranges::end(values));
486  }
487 #endif // MOMO_HAS_CONTAINERS_RANGES
488 
489  template<typename... ValueArgs>
490  std::pair<iterator, bool> emplace(ValueArgs&&... valueArgs)
491  {
492  MemManager& memManager = mHashSet.GetMemManager();
493  typename HashSet::ExtractedItem extItem;
494  typedef typename HashSet::ItemTraits::template Creator<ValueArgs...> ValueCreator;
495  extItem.Create(ValueCreator(memManager, std::forward<ValueArgs>(valueArgs)...));
496  typename HashSet::InsertResult res = mHashSet.Insert(std::move(extItem));
497  return { res.position, res.inserted };
498  }
499 
500  template<typename ValueArg>
502  std::pair<iterator, bool>> emplace(ValueArg&& valueArg)
503  {
504  typename HashSet::InsertResult res = mHashSet.InsertVar(
505  static_cast<const key_type&>(valueArg), std::forward<ValueArg>(valueArg));
506  return { res.position, res.inserted };
507  }
508 
509  template<typename... ValueArgs>
510  iterator emplace_hint(const_iterator hint, ValueArgs&&... valueArgs)
511  {
512  if MOMO_CONSTEXPR_IF (HashTraits::useHintIterators)
513  return mHashSet.AddVar(hint, std::forward<ValueArgs>(valueArgs)...);
514  else
515  return emplace(std::forward<ValueArgs>(valueArgs)...).first;
516  }
517 
519  {
520  return mHashSet.Remove(where);
521  }
522 
523  //iterator erase(iterator where)
524 
526  {
527  if (first == begin() && last == end())
528  {
529  clear();
530  return end();
531  }
532  if (first == last)
533  return first;
534  if (first != end() && std::next(first) == last)
535  return erase(first);
536  MOMO_THROW(std::invalid_argument("invalid unordered_set erase arguments"));
537  }
538 
540  {
541  return mHashSet.Remove(key) ? 1 : 0;
542  }
543 
544  template<typename ValueFilter>
545  friend size_type erase_if(unordered_set_adaptor& cont, const ValueFilter& valueFilter)
546  {
547  return cont.mHashSet.Remove(valueFilter);
548  }
549 
551  {
552  return node_type(*this, where); // need RVO for exception safety
553  }
554 
556  {
557  const_iterator iter = find(key);
558  return (iter != end()) ? extract(iter) : node_type();
559  }
560 
561  template<typename Set>
562  void merge(Set&& set)
563  {
564  mHashSet.MergeFrom(set.get_nested_container());
565  }
566 
567  size_type max_bucket_count() const noexcept
568  {
570  //return momo::internal::HashSetBuckets<Bucket>::maxBucketCount;
571  }
572 
573  size_type bucket_count() const noexcept
574  {
575  return mHashSet.GetBucketCount();
576  }
577 
578  size_type bucket_size(size_type bucketIndex) const
579  {
580  return mHashSet.GetBucketBounds(bucketIndex).GetCount();
581  }
582 
584  {
585  return mHashSet.GetBucketBounds(bucketIndex).GetBegin();
586  }
587 
589  {
590  return mHashSet.GetBucketBounds(bucketIndex).GetBegin();
591  }
592 
594  {
595  return mHashSet.GetBucketBounds(bucketIndex).GetEnd();
596  }
597 
598  const_local_iterator end(size_type bucketIndex) const
599  {
600  return mHashSet.GetBucketBounds(bucketIndex).GetEnd();
601  }
602 
604  {
605  return begin(bucketIndex);
606  }
607 
609  {
610  return end(bucketIndex);
611  }
612 
613  size_type bucket(const key_type& key) const
614  {
615  return mHashSet.GetBucketIndex(key);
616  }
617 
618  float load_factor() const noexcept
619  {
620  size_t count = size();
621  size_t bucketCount = bucket_count();
622  if (count == 0 && bucketCount == 0)
623  return 0.0;
624  return static_cast<float>(count) / static_cast<float>(bucketCount);
625  }
626 
627  friend bool operator==(const unordered_set_adaptor& left, const unordered_set_adaptor& right)
628  {
629  if (left.size() != right.size())
630  return false;
631  for (const_reference ref : left)
632  {
633  if (right.find(ref) == right.end())
634  return false;
635  }
636  return true;
637  }
638 
639  friend bool operator!=(const unordered_set_adaptor& left, const unordered_set_adaptor& right)
640  {
641  return !(left == right);
642  }
643 
644 private:
645  template<typename Iterator, typename Sentinel>
647  void> pvInsertRange(Iterator begin, Sentinel end)
648  {
649  mHashSet.Insert(std::move(begin), std::move(end));
650  }
651 
652  template<typename Iterator, typename Sentinel>
654  void> pvInsertRange(Iterator begin, Sentinel end)
655  {
656  for (Iterator iter = std::move(begin); iter != end; ++iter)
657  emplace(*iter);
658  }
659 
660 private:
661  HashSet mHashSet;
662 };
663 
686 template<typename TKey,
687  typename THasher = HashCoder<TKey>,
688  typename TEqualComparer = std::equal_to<TKey>,
689  typename TAllocator = std::allocator<TKey>>
690 class unordered_set : public unordered_set_adaptor<HashSet<TKey,
691  HashTraitsStd<TKey, THasher, TEqualComparer, HashBucketDefault>, MemManagerStd<TAllocator>>>
692 {
693 private:
697 
698 public:
699  using UnorderedSetAdaptor::UnorderedSetAdaptor;
700 
701  unordered_set& operator=(std::initializer_list<typename UnorderedSetAdaptor::value_type> values)
702  {
704  return *this;
705  }
706 
707  friend void swap(unordered_set& left, unordered_set& right) noexcept
708  {
709  left.swap(right);
710  }
711 };
712 
722 template<typename TKey,
723  typename THasher = HashCoder<TKey>,
724  typename TEqualComparer = std::equal_to<TKey>,
725  typename TAllocator = std::allocator<TKey>>
726 class unordered_set_open : public unordered_set_adaptor<HashSet<TKey,
727  HashTraitsStd<TKey, THasher, TEqualComparer, HashBucketOpenDefault>, MemManagerStd<TAllocator>>>
728 {
729 private:
733 
734 public:
735  using UnorderedSetAdaptor::UnorderedSetAdaptor;
736 
737  unordered_set_open& operator=(std::initializer_list<typename UnorderedSetAdaptor::value_type> values)
738  {
740  return *this;
741  }
742 
743  friend void swap(unordered_set_open& left, unordered_set_open& right) noexcept
744  {
745  left.swap(right);
746  }
747 };
748 
749 #ifdef MOMO_HAS_DEDUCTION_GUIDES
750 
751 #define MOMO_DECLARE_DEDUCTION_GUIDES(unordered_set) \
752 template<typename Iterator, \
753  typename Key = typename std::iterator_traits<Iterator>::value_type> \
754 unordered_set(Iterator, Iterator) \
755  -> unordered_set<Key>; \
756 template<typename Iterator, \
757  typename Key = typename std::iterator_traits<Iterator>::value_type, \
758  typename Allocator = std::allocator<Key>, \
759  typename = internal::hash_checker<Key, Allocator, HashCoder<Key>>> \
760 unordered_set(Iterator, Iterator, size_t, Allocator = Allocator()) \
761  -> unordered_set<Key, HashCoder<Key>, std::equal_to<Key>, Allocator>; \
762 template<typename Iterator, typename Hasher, \
763  typename Key = typename std::iterator_traits<Iterator>::value_type, \
764  typename Allocator = std::allocator<Key>, \
765  typename = internal::hash_checker<Key, Allocator, Hasher>> \
766 unordered_set(Iterator, Iterator, size_t, Hasher, Allocator = Allocator()) \
767  -> unordered_set<Key, Hasher, std::equal_to<Key>, Allocator>; \
768 template<typename Iterator, typename Hasher, typename EqualComparer, \
769  typename Key = typename std::iterator_traits<Iterator>::value_type, \
770  typename Allocator = std::allocator<Key>, \
771  typename = internal::hash_checker<Key, Allocator, Hasher, EqualComparer>> \
772 unordered_set(Iterator, Iterator, size_t, Hasher, EqualComparer, Allocator = Allocator()) \
773  -> unordered_set<Key, Hasher, EqualComparer, Allocator>; \
774 template<typename Key> \
775 unordered_set(std::initializer_list<Key>) \
776  -> unordered_set<Key>; \
777 template<typename Key, \
778  typename Allocator = std::allocator<Key>, \
779  typename = internal::hash_checker<Key, Allocator, HashCoder<Key>>> \
780 unordered_set(std::initializer_list<Key>, size_t, Allocator = Allocator()) \
781  -> unordered_set<Key, HashCoder<Key>, std::equal_to<Key>, Allocator>; \
782 template<typename Key, typename Hasher, \
783  typename Allocator = std::allocator<Key>, \
784  typename = internal::hash_checker<Key, Allocator, Hasher>> \
785 unordered_set(std::initializer_list<Key>, size_t, Hasher, Allocator = Allocator()) \
786  -> unordered_set<Key, Hasher, std::equal_to<Key>, Allocator>; \
787 template<typename Key, typename Hasher, typename EqualComparer, \
788  typename Allocator = std::allocator<Key>, \
789  typename = internal::hash_checker<Key, Allocator, Hasher, EqualComparer>> \
790 unordered_set(std::initializer_list<Key>, size_t, Hasher, EqualComparer, Allocator = Allocator()) \
791  -> unordered_set<Key, Hasher, EqualComparer, Allocator>; \
792 template<typename Key, typename Hasher, typename EqualComparer, typename Allocator> \
793 unordered_set(unordered_set<Key, Hasher, EqualComparer, Allocator>, momo::internal::Identity<Allocator>) \
794  -> unordered_set<Key, Hasher, EqualComparer, Allocator>;
795 
796 MOMO_DECLARE_DEDUCTION_GUIDES(unordered_set)
797 MOMO_DECLARE_DEDUCTION_GUIDES(unordered_set_open)
798 
799 #undef MOMO_DECLARE_DEDUCTION_GUIDES
800 
801 #ifdef MOMO_HAS_CONTAINERS_RANGES
802 
803 #define MOMO_DECLARE_DEDUCTION_GUIDES_RANGES(unordered_set) \
804 template<std::ranges::input_range Range, \
805  typename Key = std::ranges::range_value_t<Range>> \
806 unordered_set(std::from_range_t, Range&&) \
807  -> unordered_set<Key>; \
808 template<std::ranges::input_range Range, \
809  typename Key = std::ranges::range_value_t<Range>, \
810  typename Allocator = std::allocator<Key>, \
811  typename = internal::hash_checker<Key, Allocator, HashCoder<Key>>> \
812 unordered_set(std::from_range_t, Range&&, size_t, Allocator = Allocator()) \
813  -> unordered_set<Key, HashCoder<Key>, std::equal_to<Key>, Allocator>; \
814 template<std::ranges::input_range Range, typename Hasher, \
815  typename Key = std::ranges::range_value_t<Range>, \
816  typename Allocator = std::allocator<Key>, \
817  typename = internal::hash_checker<Key, Allocator, Hasher>> \
818 unordered_set(std::from_range_t, Range&&, size_t, Hasher, Allocator = Allocator()) \
819  -> unordered_set<Key, Hasher, std::equal_to<Key>, Allocator>; \
820 template<std::ranges::input_range Range, typename Hasher, typename EqualComparer, \
821  typename Key = std::ranges::range_value_t<Range>, \
822  typename Allocator = std::allocator<Key>, \
823  typename = internal::hash_checker<Key, Allocator, Hasher, EqualComparer>> \
824 unordered_set(std::from_range_t, Range&&, size_t, Hasher, EqualComparer, Allocator = Allocator()) \
825  -> unordered_set<Key, Hasher, EqualComparer, Allocator>;
826 
827 MOMO_DECLARE_DEDUCTION_GUIDES_RANGES(unordered_set)
828 MOMO_DECLARE_DEDUCTION_GUIDES_RANGES(unordered_set_open)
829 
830 #undef MOMO_DECLARE_DEDUCTION_GUIDES_RANGES
831 
832 #endif // MOMO_HAS_CONTAINERS_RANGES
833 
834 #endif // MOMO_HAS_DEDUCTION_GUIDES
835 
836 } // namespace stdish
837 
838 } // namespace momo
839 
840 #endif // MOMO_INCLUDE_GUARD_STDISH_UNORDERED_SET
momo::stdish::unordered_set_adaptor::erase
iterator erase(const_iterator first, const_iterator last)
Definition: unordered_set.h:525
momo::stdish::unordered_set_adaptor
Definition: unordered_set.h:32
momo::stdish::unordered_set_adaptor::const_pointer
const_iterator::Pointer const_pointer
Definition: unordered_set.h:61
momo::stdish::unordered_set_adaptor::unordered_set_adaptor
unordered_set_adaptor(Iterator first, Iterator last, size_type bucketCount, const hasher &hashFunc, const allocator_type &alloc=allocator_type())
Definition: unordered_set.h:125
momo::stdish::unordered_set_adaptor::unordered_set_adaptor
unordered_set_adaptor()
Definition: unordered_set.h:84
momo::internal::InsertResult::position
Position position
Definition: IteratorUtility.h:132
momo::stdish::unordered_set_adaptor::unordered_set_adaptor
unordered_set_adaptor(Iterator first, Iterator last, size_type bucketCount, const allocator_type &alloc=allocator_type())
Definition: unordered_set.h:117
momo::stdish::unordered_set_adaptor::max_load_factor
void max_load_factor(float maxLoadFactor)
Definition: unordered_set.h:296
momo::stdish::unordered_set_adaptor::node_type
internal::set_node_handle< typename HashSet::ExtractedItem > node_type
Definition: unordered_set.h:65
momo::internal::UIntConst::maxSize
static const size_t maxSize
Definition: Utility.h:476
momo::stdish::unordered_set_adaptor::emplace_hint
iterator emplace_hint(const_iterator hint, ValueArgs &&... valueArgs)
Definition: unordered_set.h:510
momo::stdish::unordered_set_adaptor::begin
const_iterator begin() const noexcept
Definition: unordered_set.h:267
momo::stdish::unordered_set_adaptor::insert_return_type
internal::insert_return_type< iterator, node_type > insert_return_type
Definition: unordered_set.h:66
momo::stdish::unordered_set_adaptor::insert
std::pair< iterator, bool > insert(value_type &&value)
Definition: unordered_set.h:418
momo::stdish::unordered_set_adaptor::erase
size_type erase(const key_type &key)
Definition: unordered_set.h:539
MOMO_DECLARE_PROXY_FUNCTION
#define MOMO_DECLARE_PROXY_FUNCTION(Class, Func)
Definition: Utility.h:116
MOMO_THROW
#define MOMO_THROW(exception)
Definition: UserSettings.h:191
momo::stdish::unordered_set_adaptor::key_type
HashSet::Key key_type
Definition: unordered_set.h:39
momo::internal::UIntMath::Max
static constexpr UInt Max(UInt value1, UInt value2) noexcept
Definition: Utility.h:352
momo::stdish::unordered_set_adaptor::unordered_set_adaptor
unordered_set_adaptor(unordered_set_adaptor &&right)
Definition: unordered_set.h:199
momo::stdish::unordered_set_adaptor::const_local_iterator
HashSet::ConstBucketBounds::Iterator const_local_iterator
Definition: unordered_set.h:68
momo::stdish::unordered_set_adaptor::reserve
void reserve(size_type count)
Definition: unordered_set.h:352
set_map_utility.h
momo::stdish::unordered_set_adaptor::insert
iterator insert(const_iterator hint, node_type &&node)
Definition: unordered_set.h:455
momo::stdish::unordered_set_adaptor::erase_if
friend size_type erase_if(unordered_set_adaptor &cont, const ValueFilter &valueFilter)
Definition: unordered_set.h:545
momo::stdish::internal::insert_return_type
Definition: set_map_utility.h:202
momo::internal::HashSetConstIterator::Pointer
const Item * Pointer
Definition: HashSet.h:211
momo::stdish::unordered_set_adaptor::get_nested_container
nested_container_type & get_nested_container() noexcept
Definition: unordered_set.h:262
momo::stdish::unordered_set_adaptor::max_bucket_count
size_type max_bucket_count() const noexcept
Definition: unordered_set.h:567
momo::stdish::unordered_set_adaptor::unordered_set_adaptor
unordered_set_adaptor(std::initializer_list< value_type > values, size_type bucketCount, const hasher &hashFunc, const allocator_type &alloc=allocator_type())
Definition: unordered_set.h:151
momo::stdish::unordered_set_adaptor::operator=
unordered_set_adaptor & operator=(unordered_set_adaptor &&right) noexcept(momo::internal::ContainerAssignerStd::IsNothrowMoveAssignable< unordered_set_adaptor >::value)
Definition: unordered_set.h:230
momo::internal::UIntMath::Log2
static UInt Log2(UInt value) noexcept
Definition: Utility.h:414
momo::stdish::unordered_set_adaptor::unordered_set_adaptor
unordered_set_adaptor(std::initializer_list< value_type > values)
Definition: unordered_set.h:140
momo::stdish::unordered_set_adaptor::allocator_type
std::allocator_traits< typename MemManager::ByteAllocator >::template rebind_alloc< value_type > allocator_type
Definition: unordered_set.h:50
momo::stdish::unordered_set_adaptor::unordered_set_adaptor
unordered_set_adaptor(size_type bucketCount, const allocator_type &alloc=allocator_type())
Definition: unordered_set.h:93
momo::stdish::unordered_set_adaptor::empty
MOMO_NODISCARD bool empty() const noexcept
Definition: unordered_set.h:334
momo::stdish::unordered_set_adaptor::extract
node_type extract(const key_type &key)
Definition: unordered_set.h:555
momo::stdish::unordered_set_adaptor::equal_range
MOMO_FORCEINLINE momo::internal::EnableIf< IsValidKeyArg< KeyArg >::value, std::pair< const_iterator, const_iterator > > equal_range(const KeyArg &key) const
Definition: unordered_set.h:409
momo::internal::HashSetConstIterator::Reference
const Item & Reference
Definition: HashSet.h:210
momo::stdish::set
momo::stdish::set is similar to std::set, but much more efficient in memory usage....
Definition: set.h:690
momo::stdish::unordered_set_adaptor::unordered_set_adaptor
unordered_set_adaptor(size_type bucketCount, const hasher &hashFunc, const key_equal &equalComp, const allocator_type &alloc=allocator_type())
Definition: unordered_set.h:104
momo::MemManagerStd
MemManagerStd uses allocator<unsigned char>::allocate and deallocate
Definition: MemManager.h:179
momo::stdish::unordered_set_adaptor::reference
value_type & reference
Definition: unordered_set.h:56
momo::stdish::unordered_set_adaptor::unordered_set_adaptor
unordered_set_adaptor(Iterator first, Iterator last, size_type bucketCount, const hasher &hashFunc, const key_equal &equalComp, const allocator_type &alloc=allocator_type())
Definition: unordered_set.h:133
momo::stdish::unordered_set_adaptor::begin
local_iterator begin(size_type bucketIndex)
Definition: unordered_set.h:583
momo::stdish::unordered_set_adaptor::contains
MOMO_FORCEINLINE bool contains(const key_type &key) const
Definition: unordered_set.h:387
momo::stdish::unordered_set_adaptor::cend
const_iterator cend() const noexcept
Definition: unordered_set.h:286
momo::stdish::unordered_set_adaptor::cend
const_local_iterator cend(size_type bucketIndex) const
Definition: unordered_set.h:608
momo::stdish::unordered_set_adaptor::~unordered_set_adaptor
~unordered_set_adaptor()=default
momo::stdish::unordered_set_adaptor::get_allocator
allocator_type get_allocator() const noexcept
Definition: unordered_set.h:319
momo::internal::ContainerAssignerStd::Move
static Container & Move(Container &&srcCont, Container &dstCont) noexcept(IsNothrowMoveAssignable< Container >::value)
Definition: Utility.h:515
momo::internal::InsertResult
Definition: IteratorUtility.h:100
momo::internal::HashSetConstIterator
Definition: HashSet.h:289
momo::stdish::unordered_set_adaptor::pointer
value_type * pointer
Definition: unordered_set.h:60
momo::stdish::unordered_set_adaptor::key_eq
key_equal key_eq() const
Definition: unordered_set.h:314
momo::stdish::unordered_set_adaptor::insert
std::pair< iterator, bool > insert(const value_type &value)
Definition: unordered_set.h:432
momo::stdish::unordered_set_adaptor::count
MOMO_FORCEINLINE momo::internal::EnableIf< IsValidKeyArg< KeyArg >::value, size_type > count(const KeyArg &key) const
Definition: unordered_set.h:382
momo::stdish::unordered_set_adaptor::unordered_set_adaptor
unordered_set_adaptor(const allocator_type &alloc)
Definition: unordered_set.h:88
momo::stdish::unordered_set_adaptor::operator=
unordered_set_adaptor & operator=(std::initializer_list< value_type > values)
Definition: unordered_set.h:241
momo::HashSetCore::MemManager
ItemTraits::MemManager MemManager
Definition: HashSet.h:481
momo::stdish::unordered_set_adaptor::difference_type
ptrdiff_t difference_type
Definition: unordered_set.h:46
momo::internal::EnableIf
typename std::enable_if< value, Type >::type EnableIf
Definition: Utility.h:199
momo::stdish::unordered_set_adaptor::get_nested_container
const nested_container_type & get_nested_container() const noexcept
Definition: unordered_set.h:257
momo::stdish::unordered_set_adaptor::erase
iterator erase(const_iterator where)
Definition: unordered_set.h:518
momo::stdish::unordered_set_adaptor::operator!=
friend bool operator!=(const unordered_set_adaptor &left, const unordered_set_adaptor &right)
Definition: unordered_set.h:639
momo::stdish::unordered_set_adaptor::end
const_iterator end() const noexcept
Definition: unordered_set.h:274
momo::stdish::unordered_set_adaptor::find
MOMO_FORCEINLINE momo::internal::EnableIf< IsValidKeyArg< KeyArg >::value, const_iterator > find(const KeyArg &key) const
Definition: unordered_set.h:366
momo
Definition: Array.h:27
momo::stdish::unordered_set_adaptor::max_size
size_type max_size() const noexcept
Definition: unordered_set.h:324
momo::internal::ContainerAssignerStd::IsNothrowMoveAssignable
BoolConstant< std::is_empty< Allocator >::value||std::allocator_traits< Allocator >::propagate_on_container_move_assignment::value > IsNothrowMoveAssignable
Definition: Utility.h:511
momo::stdish::unordered_set_adaptor::end
local_iterator end(size_type bucketIndex)
Definition: unordered_set.h:593
momo::stdish::unordered_set_adaptor::max_load_factor
float max_load_factor() const noexcept
Definition: unordered_set.h:291
momo::HashCoder< TKey >
momo::stdish::unordered_set_adaptor::insert
iterator insert(const_iterator hint, value_type &&value)
Definition: unordered_set.h:424
momo::stdish::unordered_set::operator=
unordered_set & operator=(std::initializer_list< typename UnorderedSetAdaptor::value_type > values)
Definition: unordered_set.h:701
momo::internal::InsertResult::inserted
bool inserted
Definition: IteratorUtility.h:135
momo::stdish::unordered_set_adaptor::unordered_set_adaptor
unordered_set_adaptor(const unordered_set_adaptor &right, const allocator_type &alloc)
Definition: unordered_set.h:223
momo::stdish::unordered_set_adaptor::size
size_type size() const noexcept
Definition: unordered_set.h:329
momo::stdish::unordered_set_adaptor::insert
iterator insert(const_iterator hint, const value_type &value)
Definition: unordered_set.h:438
momo::stdish::unordered_set_adaptor::equal_range
MOMO_FORCEINLINE std::pair< const_iterator, const_iterator > equal_range(const key_type &key) const
Definition: unordered_set.h:399
momo::stdish::unordered_set_adaptor::count
MOMO_FORCEINLINE size_type count(const key_type &key) const
Definition: unordered_set.h:375
momo::stdish::unordered_set_adaptor::iterator
HashSet::Iterator iterator
Definition: unordered_set.h:53
momo::HashSetCore
Definition: HashSet.h:474
momo::stdish::unordered_set_adaptor::insert
void insert(Iterator first, Iterator last)
Definition: unordered_set.h:470
momo::stdish::unordered_set_adaptor::operator==
friend bool operator==(const unordered_set_adaptor &left, const unordered_set_adaptor &right)
Definition: unordered_set.h:627
momo::stdish::unordered_set_adaptor::hash_function
hasher hash_function() const
Definition: unordered_set.h:309
momo::stdish::unordered_set_adaptor::swap
friend void swap(unordered_set_adaptor &left, unordered_set_adaptor &right) noexcept
Definition: unordered_set.h:252
momo::stdish::unordered_set_adaptor::begin
const_local_iterator begin(size_type bucketIndex) const
Definition: unordered_set.h:588
momo::stdish::unordered_set_open
momo::stdish::unordered_set_open is similar to std::unordered_set, but much more efficient in operati...
Definition: unordered_set.h:728
momo::stdish::unordered_set_adaptor::merge
void merge(Set &&set)
Definition: unordered_set.h:562
momo::stdish::unordered_set_adaptor::extract
node_type extract(const_iterator where)
Definition: unordered_set.h:550
momo::stdish::unordered_set_adaptor::contains
MOMO_FORCEINLINE momo::internal::EnableIf< IsValidKeyArg< KeyArg >::value, bool > contains(const KeyArg &key) const
Definition: unordered_set.h:394
momo::stdish::unordered_set_adaptor::unordered_set_adaptor
unordered_set_adaptor(std::initializer_list< value_type > values, size_type bucketCount, const allocator_type &alloc=allocator_type())
Definition: unordered_set.h:145
momo::HashTraitsStd
Definition: HashTraits.h:196
momo::stdish::unordered_set_adaptor::emplace
std::pair< iterator, bool > emplace(ValueArgs &&... valueArgs)
Definition: unordered_set.h:490
momo::stdish::unordered_set_adaptor::emplace
momo::internal::EnableIf< std::is_same< key_type, typename std::decay< ValueArg >::type >::value, std::pair< iterator, bool > > emplace(ValueArg &&valueArg)
Definition: unordered_set.h:502
momo::stdish::unordered_set_adaptor::size_type
size_t size_type
Definition: unordered_set.h:45
momo::stdish::unordered_set_adaptor::local_iterator
const_local_iterator local_iterator
Definition: unordered_set.h:69
momo::stdish::unordered_set_adaptor::insert
void insert(std::initializer_list< value_type > values)
Definition: unordered_set.h:475
momo::stdish::unordered_set_adaptor::hasher
HashTraits::Hasher hasher
Definition: unordered_set.h:40
momo::stdish::unordered_set_adaptor::value_type
key_type value_type
Definition: unordered_set.h:48
momo::stdish::unordered_set_adaptor::nested_container_type
HashSet nested_container_type
Definition: unordered_set.h:43
momo::stdish::unordered_set_adaptor::bucket_size
size_type bucket_size(size_type bucketIndex) const
Definition: unordered_set.h:578
momo::stdish::unordered_set_adaptor::cbegin
const_local_iterator cbegin(size_type bucketIndex) const
Definition: unordered_set.h:603
momo::stdish::unordered_set_adaptor::insert
insert_return_type insert(node_type &&node)
Definition: unordered_set.h:446
momo::HashSetCore::Key
ItemTraits::Key Key
Definition: HashSet.h:479
MOMO_CONSTEXPR_IF
#define MOMO_CONSTEXPR_IF
Definition: UserSettings.h:228
momo::stdish::unordered_set_adaptor::bucket
size_type bucket(const key_type &key) const
Definition: unordered_set.h:613
std
Definition: Array.h:1178
momo::stdish::unordered_set_adaptor::unordered_set_adaptor
unordered_set_adaptor(std::initializer_list< value_type > values, size_type bucketCount, const hasher &hashFunc, const key_equal &equalComp, const allocator_type &alloc=allocator_type())
Definition: unordered_set.h:157
MOMO_FORCEINLINE
#define MOMO_FORCEINLINE
Definition: UserSettings.h:125
momo::HashSetCore::HashTraits
THashTraits HashTraits
Definition: HashSet.h:477
momo::internal::SetExtractedItem::Create
void Create(ItemCreator &&itemCreator)
Definition: SetUtility.h:322
momo::stdish::unordered_set_adaptor::swap
void swap(unordered_set_adaptor &right) noexcept
Definition: unordered_set.h:247
momo::stdish::unordered_set_adaptor::clear
void clear() noexcept
Definition: unordered_set.h:339
momo::stdish::internal::set_node_handle
Definition: set_map_utility.h:42
momo::stdish::unordered_set_adaptor::const_reference
const_iterator::Reference const_reference
Definition: unordered_set.h:57
momo::stdish::unordered_set_open::operator=
unordered_set_open & operator=(std::initializer_list< typename UnorderedSetAdaptor::value_type > values)
Definition: unordered_set.h:737
momo::stdish::unordered_set_adaptor::unordered_set_adaptor
unordered_set_adaptor(const unordered_set_adaptor &right)
Definition: unordered_set.h:218
momo::internal::ContainerAssignerStd::Copy
static Container & Copy(const Container &srcCont, Container &dstCont)
Definition: Utility.h:531
momo::stdish::unordered_set_adaptor::const_iterator
HashSet::ConstIterator const_iterator
Definition: unordered_set.h:52
momo::stdish::unordered_set
momo::stdish::unordered_set is similar to std::unordered_set, but much more efficient in memory usage...
Definition: unordered_set.h:692
momo::stdish::unordered_set_adaptor::unordered_set_adaptor
unordered_set_adaptor(unordered_set_adaptor &&right, const allocator_type &alloc)
Definition: unordered_set.h:204
momo::stdish::unordered_set_adaptor::end
const_local_iterator end(size_type bucketIndex) const
Definition: unordered_set.h:598
momo::stdish::unordered_set_adaptor::rehash
void rehash(size_type bucketCount)
Definition: unordered_set.h:344
momo::stdish::set_adaptor::get_nested_container
const nested_container_type & get_nested_container() const noexcept
Definition: set.h:203
momo::stdish::unordered_set_adaptor::unordered_set_adaptor
unordered_set_adaptor(Iterator first, Iterator last)
Definition: unordered_set.h:111
momo::stdish::unordered_set::swap
friend void swap(unordered_set &left, unordered_set &right) noexcept
Definition: unordered_set.h:707
momo::stdish::unordered_set_adaptor::cbegin
const_iterator cbegin() const noexcept
Definition: unordered_set.h:281
momo::HashSetCore::bucketMaxItemCount
static const size_t bucketMaxItemCount
Definition: HashSet.h:512
momo::internal::SetExtractedItem
Definition: SetUtility.h:257
momo::internal::ContainerAssignerStd::Swap
static void Swap(Container &cont1, Container &cont2) noexcept
Definition: Utility.h:546
momo::stdish::unordered_set_adaptor::unordered_set_adaptor
unordered_set_adaptor(size_type bucketCount, const hasher &hashFunc, const allocator_type &alloc=allocator_type())
Definition: unordered_set.h:98
momo::stdish::unordered_set_adaptor::key_equal
HashTraits::EqualComparer key_equal
Definition: unordered_set.h:41
momo::stdish::unordered_set_adaptor::bucket_count
size_type bucket_count() const noexcept
Definition: unordered_set.h:573
momo::stdish::unordered_set_adaptor::operator=
unordered_set_adaptor & operator=(const unordered_set_adaptor &right)
Definition: unordered_set.h:236
momo::stdish::unordered_set_adaptor::find
MOMO_FORCEINLINE const_iterator find(const key_type &key) const
Definition: unordered_set.h:357
MOMO_NODISCARD
#define MOMO_NODISCARD
Definition: UserSettings.h:262
momo::stdish::unordered_set_adaptor::load_factor
float load_factor() const noexcept
Definition: unordered_set.h:618
momo::stdish::unordered_set_open::swap
friend void swap(unordered_set_open &left, unordered_set_open &right) noexcept
Definition: unordered_set.h:743