Skip to content

Commit d06c191

Browse files
committed
P0920R2 Precalculated hash values in lookup
1 parent 6f34b05 commit d06c191

File tree

2 files changed

+149
-3
lines changed

2 files changed

+149
-3
lines changed

source/containers.tex

Lines changed: 147 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2293,6 +2293,7 @@
22932293
\item \tcode{n} denotes a value of type \tcode{size_type},
22942294
\item \tcode{z} denotes a value of type \tcode{float}, and
22952295
\item \tcode{nh} denotes a non-const rvalue of type \tcode{X::node_type}.
2296+
\item \tcode{hk} and \tcode{hke} denote values of type \tcode{size_t}.
22962297
\end{itemize}
22972298

22982299
% Local command to index names as members of all unordered containers.
@@ -2746,12 +2747,29 @@
27462747
& Average case \bigoh{1}, worst case \bigoh{\tcode{b.size()}}.
27472748
\\ \rowsep
27482749
%
2750+
\tcode{b.find(k, hk)}
2751+
& \tcode{iterator}; \br \tcode{const_iterator} for const \tcode{b}.
2752+
& \expects \tcode{b.hash_function()(k)} equals \tcode{hk}.\br
2753+
\returns an iterator pointing to an element with key equivalent to
2754+
\tcode{k}, or \tcode{b.end()} if no such element exists.
2755+
& Average case \bigoh{1}, worst case \bigoh{\tcode{b.size()}}.
2756+
\\ \rowsep
2757+
%
27492758
\tcode{a_tran.find(ke)}
27502759
& \tcode{iterator}; \br \tcode{const_iterator} for const \tcode{a_tran}.
27512760
& Returns an iterator pointing to an element with key equivalent to
27522761
\tcode{ke}, or \tcode{a_tran.end()} if no such element exists.%
27532762
& Average case \bigoh{1},
2754-
worst case \bigoh{\tcode{a_tran.}\br{}\tcode{size()}}. % avoid wverfull
2763+
worst case \bigoh{\tcode{a_tran.}\br{}\tcode{size()}}. % avoid overfull
2764+
\\ \rowsep
2765+
%
2766+
\tcode{a_tran.find(ke, hke)}
2767+
& \tcode{iterator}; \br \tcode{const_iterator} for const \tcode{a_tran}.
2768+
& \expects \tcode{a_tran.hash_function()(ke)} equals \tcode{hke}.\br
2769+
\returns an iterator pointing to an element with key equivalent to
2770+
\tcode{ke}, or \tcode{a_tran.end()} if no such element exists.%
2771+
& Average case \bigoh{1},
2772+
worst case \bigoh{\tcode{a_tran.}\br{}\tcode{size()}}. % avoid overfull
27552773
\\ \rowsep
27562774
%
27572775
\indexunordmem{count}%
@@ -2761,6 +2779,13 @@
27612779
& Average case \bigoh{\tcode{b.count(k)}}, worst case \bigoh{\tcode{b.size()}}.
27622780
\\ \rowsep
27632781
%
2782+
\tcode{b.count(k, hk)}
2783+
& \tcode{size_type}
2784+
& \expects \tcode{b.hash_function()(k)} equals \tcode{hk}.\br
2785+
\returns the number of elements with key equivalent to \tcode{k}.%
2786+
& Average case \bigoh{\tcode{b.count(k)}}, worst case \bigoh{\tcode{b.size()}}.
2787+
\\ \rowsep
2788+
%
27642789
\tcode{a_tran.count(ke)}
27652790
& \tcode{size_type}
27662791
& Returns the number of elements with key equivalent to \tcode{ke}.%
@@ -2769,16 +2794,40 @@
27692794
worst case \bigoh{\tcode{a_tran.}\br{}\tcode{size()}}. % avoid overfull
27702795
\\ \rowsep
27712796
%
2797+
\tcode{a_tran.count(ke, hke)}
2798+
& \tcode{size_type}
2799+
& \expects \tcode{b.hash_function()(ke)} equals \tcode{hke}.\br
2800+
\returns the number of elements with key equivalent to \tcode{ke}.%
2801+
& Average case
2802+
\bigoh{\tcode{a_tran.}\br{}\tcode{count(ke)}}, % avoid overfull
2803+
worst case \bigoh{\tcode{a_tran.}\br{}\tcode{size()}}. % avoid overfull
2804+
\\ \rowsep
2805+
%
27722806
\indexunordmem{contains}%
27732807
\tcode{b.contains(k)}
27742808
& \tcode{bool}
2775-
& Equivalent to \tcode{b.find(k) != b.end()}%
2809+
& \effects Equivalent to \tcode{b.find(k) != b.end()}%
2810+
& Average case \bigoh{1}, worst case \bigoh{\tcode{b.size()}}.
2811+
\\ \rowsep
2812+
%
2813+
\tcode{b.contains(k, hk)}
2814+
& \tcode{bool}
2815+
& \expects \tcode{b.hash_function()(ke)} equals \tcode{hke}.\br
2816+
\effects Equivalent to \tcode{b.find(k) != b.end()}%
27762817
& Average case \bigoh{1}, worst case \bigoh{\tcode{b.size()}}.
27772818
\\ \rowsep
27782819
%
27792820
\tcode{a_tran.contains(ke)}
27802821
& \tcode{bool}
2781-
& Equivalent to \tcode{a_tran.find(ke) != a_tran.end()}%
2822+
& \effects Equivalent to \tcode{a_tran.find(ke) != a_tran.end()}%
2823+
& Average case \bigoh{1},
2824+
worst case \bigoh{\tcode{a_tran.}\br{}\tcode{size()}}. % avoid overfull
2825+
\\ \rowsep
2826+
%
2827+
\tcode{a_tran.contains(ke, hke)}
2828+
& \tcode{bool}
2829+
& \expects \tcode{a_tran.hash_function()(ke)} equals \tcode{hke}.\br
2830+
\effects Equivalent to \tcode{a_tran.find(ke, hke) != a_tran.end()}%
27822831
& Average case \bigoh{1},
27832832
worst case \bigoh{\tcode{a_tran.}\br{}\tcode{size()}}. % avoid overfull
27842833
\\ \rowsep
@@ -2794,6 +2843,17 @@
27942843
\bigoh{\tcode{b.size()}}.
27952844
\\ \rowsep
27962845
%
2846+
\tcode{b.equal_range(k, hk)}
2847+
& \tcode{pair<iterator, iterator>}; \br
2848+
\tcode{pair<const_iterator, const_iterator>} for const \tcode{b}.
2849+
& \expects \tcode{b.hash_function()(k)} equals \tcode{hk}.\br
2850+
\returns a range containing all elements with keys equivalent to
2851+
\tcode{k}. Returns \tcode{make_pair(b.end(), b.end())} if
2852+
no such elements exist.%
2853+
& Average case \bigoh{\tcode{b.count(k)}}. Worst case
2854+
\bigoh{\tcode{b.size()}}.
2855+
\\ \rowsep
2856+
%
27972857
\tcode{a_tran.equal_range(ke)}
27982858
& \tcode{pair<iterator, iterator>}; \br
27992859
\tcode{pair<const_iterator, const_iterator>} for const \tcode{a_tran}.
@@ -2804,6 +2864,18 @@
28042864
\bigoh{\tcode{a_tran.}\br{}\tcode{count(ke)}}. % avoid overfull
28052865
Worst case \bigoh{\tcode{a_tran.}\br{}\tcode{size()}}. % avoid overfull
28062866
\\ \rowsep
2867+
%
2868+
\tcode{a_tran.equal_range(ke, hke)}
2869+
& \tcode{pair<iterator, iterator>}; \br
2870+
\tcode{pair<const_iterator, const_iterator>} for const \tcode{a_tran}.
2871+
& \expects \tcode{a_tran.hash_function()(ke)} equals \tcode{hke}.\br
2872+
\returns a range containing all elements with keys equivalent to
2873+
\tcode{ke}. Returns \tcode{make_pair(a_tran.end(), a_tran.end())} if
2874+
no such elements exist.%
2875+
& Average case
2876+
\bigoh{\tcode{a_tran.}\br{}\tcode{count(ke)}}. % avoid overfull
2877+
Worst case \bigoh{\tcode{a_tran.}\br{}\tcode{size()}}. % avoid overfull
2878+
\\ \rowsep
28072879
\indexunordmem{bucket_count}%
28082880
\tcode{b.bucket_count()}
28092881
& \tcode{size_type}
@@ -7939,22 +8011,40 @@
79398011
// map operations
79408012
iterator find(const key_type& k);
79418013
const_iterator find(const key_type& k) const;
8014+
iterator find(const key_type& k, size_t hash);
8015+
const_iterator find(const key_type& k, size_t hash) const;
79428016
template <class K>
79438017
iterator find(const K& k);
79448018
template <class K>
79458019
const_iterator find(const K& k) const;
8020+
template <class K>
8021+
iterator find(const K& k, size_t hash);
8022+
template <class K>
8023+
const_iterator find(const K& k, size_t hash) const;
79468024
size_type count(const key_type& k) const;
8025+
size_type count(const key_type& k, size_t hash) const;
79478026
template <class K>
79488027
size_type count(const K& k) const;
8028+
template <class K>
8029+
size_type count(const K& k, size_t hash) const;
79498030
bool contains(const key_type& k) const;
8031+
bool contains(const key_type& k, size_t hash) const;
79508032
template <class K>
79518033
bool contains(const K& k) const;
8034+
template <class K>
8035+
bool contains(const K& k, size_t hash) const;
79528036
pair<iterator, iterator> equal_range(const key_type& k);
79538037
pair<const_iterator, const_iterator> equal_range(const key_type& k) const;
8038+
pair<iterator, iterator> equal_range(const key_type& k, size_t hash);
8039+
pair<const_iterator, const_iterator> equal_range(const key_type& k, size_t hash) const;
79548040
template <class K>
79558041
pair<iterator, iterator> equal_range(const K& k);
79568042
template <class K>
79578043
pair<const_iterator, const_iterator> equal_range(const K& k) const;
8044+
template <class K>
8045+
pair<iterator, iterator> equal_range(const K& k, size_t hash);
8046+
template <class K>
8047+
pair<const_iterator, const_iterator> equal_range(const K& k, size_t hash) const;
79588048

79598049
// \ref{unord.map.elem}, element access
79608050
mapped_type& operator[](const key_type& k);
@@ -8503,22 +8593,40 @@
85038593
// map operations
85048594
iterator find(const key_type& k);
85058595
const_iterator find(const key_type& k) const;
8596+
iterator find(const key_type& k, size_t hash);
8597+
const_iterator find(const key_type& k, size_t hash) const;
85068598
template <class K>
85078599
iterator find(const K& k);
85088600
template <class K>
85098601
const_iterator find(const K& k) const;
8602+
template <class K>
8603+
iterator find(const K& k, size_t hash);
8604+
template <class K>
8605+
const_iterator find(const K& k, size_t hash) const;
85108606
size_type count(const key_type& k) const;
8607+
size_type count(const key_type& k, size_t hash) const;
85118608
template <class K>
85128609
size_type count(const K& k) const;
8610+
template <class K>
8611+
size_type count(const K& k, size_t hash) const;
85138612
bool contains(const key_type& k) const;
8613+
bool contains(const key_type& k, size_t hash) const;
85148614
template <class K>
85158615
bool contains(const K& k) const;
8616+
template <class K>
8617+
bool contains(const K& k, size_t hash) const;
85168618
pair<iterator, iterator> equal_range(const key_type& k);
85178619
pair<const_iterator, const_iterator> equal_range(const key_type& k) const;
8620+
pair<iterator, iterator> equal_range(const key_type& k, size_t hash);
8621+
pair<const_iterator, const_iterator> equal_range(const key_type& k, size_t hash) const;
85188622
template <class K>
85198623
pair<iterator, iterator> equal_range(const K& k);
85208624
template <class K>
85218625
pair<const_iterator, const_iterator> equal_range(const K& k) const;
8626+
template <class K>
8627+
pair<iterator, iterator> equal_range(const K& k, size_t hash);
8628+
template <class K>
8629+
pair<const_iterator, const_iterator> equal_range(const K& k, size_t hash) const;
85228630

85238631
// bucket interface
85248632
size_type bucket_count() const noexcept;
@@ -8865,22 +8973,40 @@
88658973
// set operations
88668974
iterator find(const key_type& k);
88678975
const_iterator find(const key_type& k) const;
8976+
iterator find(const key_type& k, size_t hash);
8977+
const_iterator find(const key_type& k, size_t hash) const;
88688978
template <class K>
88698979
iterator find(const K& k);
88708980
template <class K>
88718981
const_iterator find(const K& k) const;
8982+
template <class K>
8983+
iterator find(const K& k, size_t hash);
8984+
template <class K>
8985+
const_iterator find(const K& k, size_t hash) const;
88728986
size_type count(const key_type& k) const;
8987+
size_type count(const key_type& k, size_t hash) const;
88738988
template <class K>
88748989
size_type count(const K& k) const;
8990+
template <class K>
8991+
size_type count(const K& k, size_t hash) const;
88758992
bool contains(const key_type& k) const;
8993+
bool contains(const key_type& k, size_t hash) const;
88768994
template <class K>
88778995
bool contains(const K& k) const;
8996+
template <class K>
8997+
bool contains(const K& k, size_t hash) const;
88788998
pair<iterator, iterator> equal_range(const key_type& k);
88798999
pair<const_iterator, const_iterator> equal_range(const key_type& k) const;
9000+
pair<iterator, iterator> equal_range(const key_type& k, size_t hash);
9001+
pair<const_iterator, const_iterator> equal_range(const key_type& k, size_t hash) const;
88809002
template <class K>
88819003
pair<iterator, iterator> equal_range(const K& k);
88829004
template <class K>
88839005
pair<const_iterator, const_iterator> equal_range(const K& k) const;
9006+
template <class K>
9007+
pair<iterator, iterator> equal_range(const K& k, size_t hash);
9008+
template <class K>
9009+
pair<const_iterator, const_iterator> equal_range(const K& k, size_t hash) const;
88849010

88859011
// bucket interface
88869012
size_type bucket_count() const noexcept;
@@ -9189,22 +9315,40 @@
91899315
// set operations
91909316
iterator find(const key_type& k);
91919317
const_iterator find(const key_type& k) const;
9318+
iterator find(const key_type& k, size_t hash);
9319+
const_iterator find(const key_type& k, size_t hash) const;
91929320
template <class K>
91939321
iterator find(const K& k);
91949322
template <class K>
91959323
const_iterator find(const K& k) const;
9324+
template <class K>
9325+
iterator find(const K& k, size_t hash);
9326+
template <class K>
9327+
const_iterator find(const K& k, size_t hash) const;
91969328
size_type count(const key_type& k) const;
9329+
size_type count(const key_type& k, size_t hash) const;
91979330
template <class K>
91989331
size_type count(const K& k) const;
9332+
template <class K>
9333+
size_type count(const K& k, size_t hash) const;
91999334
bool contains(const key_type& k) const;
9335+
bool contains(const key_type& k, size_t hash) const;
92009336
template <class K>
92019337
bool contains(const K& k) const;
9338+
template <class K>
9339+
bool contains(const K& k, size_t hash) const;
92029340
pair<iterator, iterator> equal_range(const key_type& k);
92039341
pair<const_iterator, const_iterator> equal_range(const key_type& k) const;
9342+
pair<iterator, iterator> equal_range(const key_type& k, size_t hash);
9343+
pair<const_iterator, const_iterator> equal_range(const key_type& k, size_t hash) const;
92049344
template <class K>
92059345
pair<iterator, iterator> equal_range(const K& k);
92069346
template <class K>
92079347
pair<const_iterator, const_iterator> equal_range(const K& k) const;
9348+
template <class K>
9349+
pair<iterator, iterator> equal_range(const K& k, size_t hash);
9350+
template <class K>
9351+
pair<const_iterator, const_iterator> equal_range(const K& k, size_t hash) const;
92089352

92099353
// bucket interface
92109354
size_type bucket_count() const noexcept;

source/support.tex

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -602,6 +602,8 @@
602602
\tcode{<map>} \tcode{<set>} \\ \rowsep
603603
\defnlibxname{cpp_lib_generic_unordered_lookup} & \tcode{201811L} &
604604
\tcode{<unordered_map>} \tcode{<unordered_set>} \\ \rowsep
605+
\defnlibxname{cpp_lib_generic_unordered_hash_lookup} & \tcode{201902L} &
606+
\tcode{<unordered_map>} \tcode{<unordered_set>} \\ \rowsep
605607
\defnlibxname{cpp_lib_hardware_interference_size} & \tcode{201703L} &
606608
\tcode{<new>} \\ \rowsep
607609
\defnlibxname{cpp_lib_has_unique_object_representations} & \tcode{201606L} &

0 commit comments

Comments
 (0)