Topic: Heterogeneous lookup in unordered containers
Author: Roman Orlov <mr.gordon.freman@gmail.com>
Date: Fri, 7 Apr 2017 05:28:55 -0700 (PDT)
Raw View
------=_Part_446_1554885244.1491568135990
Content-Type: multipart/alternative;
boundary="----=_Part_447_1499587926.1491568135991"
------=_Part_447_1499587926.1491568135991
Content-Type: text/plain; charset=UTF-8
Hello,
I'd like to search for elements in a key-based container via
std::string_view without construction of std::string instance. It is
possible for std::map/std::set if I explicitly declare geterogeneous (or
transparent) compare function.
std::map<std::string, std::less<>> m;
m.find(std::string_view{"hello"});
It is done via generic lookup functions which are enabled if a compare
function is transparent. Unfortunately, there are now such functions for
unordered containers.
I've found a proposal for fixing this
http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2013/n3573.html
But it's rather old and I don't like it for several reasons. I believe the
C++ committee dislikes it too)
1) It proposes heterogeneous hash function which forwards type T as
std::decay<T>. I consider this a bad practice because std::decay can
destroy initial type (remember array-to-pointer conversion).
2) Heterogeneous lookup is enabled by default
template<typename T, typename Hash = std::hash<>, typename Eq = std::
equal_to<>>
iterator find(T t, Hash h = Hash(), Eq e = Eq());
That's wrong and breaks an old code
some_map.find({100, 'A'});
Also it makes the functions ugly.
Now I work on my own proposal to make heterogeneous lookup in unordered
containers better.
Instead of implementing std::hash<> via std::decay<T> I propose more safe
approach
template <>
struct hash<void> {
template <typename T>
size_t operator()(T&& v) const noexcept {
return hash<typename remove_cv<typename remove_reference<T>::type>::
type>{}(v);
}
typedef void is_transparent;
};
If an unordered container is declared with transparent hash then the
*default* compare function should be transparent too. It may look like this
template <class _Value, class _Hash>
struct _default_pred {
typedef equal_to<_Value> type;
};
template <class _Value>
struct _default_pred< _Value, hash<> > {
typedef equal_to<> type;
};
template <class _Value, class _Hash = hash<_Value>,
class _Pred = typename _default_pred<_Value, _Hash>::type,
class _Alloc = allocator<_Value> >
class unordered_set
Then the heterogeneous lookup functions may be enabled via SFINAE if the
hash and compare functions are both transparent.
template <class _K2, class _Rt>
using __enable_if_transparent = typename enable_if<
__is_transparent<_Hash, _K2>::value &&
__is_transparent<_Pred, _K2>::value, _Rt>::type;
template <class _K2>
__enable_if_transparent<_K2, iterator> find(const _K2& __k);
I have implemented this for std::unordered_set in libc++
https://github.com/compmaniak/libcxx/pull/1/files
The solution is the same for unordered set/multiset/map/multimap.
What do you think about all of this? Any thoughts would be appreciated.
Or maybe somebody has already done it better.
Thanks,
--
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
To view this discussion on the web visit https://groups.google.com/a/isocpp.org/d/msgid/std-proposals/aba58f0f-6180-49a7-bf87-8f2a881666cc%40isocpp.org.
------=_Part_447_1499587926.1491568135991
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr"><div>Hello,</div><div><br></div><div>I'd like to searc=
h for elements in a key-based container via std::string_view without constr=
uction of std::string instance. It is possible for std::map/std::set if I e=
xplicitly declare geterogeneous (or transparent) compare function.</div><di=
v class=3D"prettyprint" style=3D"background-color: rgb(250, 250, 250); bord=
er-color: rgb(187, 187, 187); border-style: solid; border-width: 1px; word-=
wrap: break-word;"><code class=3D"prettyprint"><div class=3D"subprettyprint=
"><span style=3D"color: #000;" class=3D"styled-by-prettify">std</span><span=
style=3D"color: #660;" class=3D"styled-by-prettify">::</span><span style=
=3D"color: #000;" class=3D"styled-by-prettify">map</span><span style=3D"col=
or: #660;" class=3D"styled-by-prettify"><</span><span style=3D"color: #0=
00;" class=3D"styled-by-prettify">std</span><span style=3D"color: #660;" cl=
ass=3D"styled-by-prettify">::</span><span style=3D"color: #008;" class=3D"s=
tyled-by-prettify">string</span><span style=3D"color: #660;" class=3D"style=
d-by-prettify">,</span><span style=3D"color: #000;" class=3D"styled-by-pret=
tify"> std</span><span style=3D"color: #660;" class=3D"styled-by-prettify">=
::</span><span style=3D"color: #000;" class=3D"styled-by-prettify">less</sp=
an><span style=3D"color: #660;" class=3D"styled-by-prettify"><>></=
span><span style=3D"color: #000;" class=3D"styled-by-prettify"> m</span><sp=
an style=3D"color: #660;" class=3D"styled-by-prettify">;</span><span style=
=3D"color: #000;" class=3D"styled-by-prettify"><br>m</span><span style=3D"c=
olor: #660;" class=3D"styled-by-prettify">.</span><span style=3D"color: #00=
0;" class=3D"styled-by-prettify">find</span><span style=3D"color: #660;" cl=
ass=3D"styled-by-prettify">(</span><span style=3D"color: #000;" class=3D"st=
yled-by-prettify">std</span><span style=3D"color: #660;" class=3D"styled-by=
-prettify">::</span><span style=3D"color: #000;" class=3D"styled-by-prettif=
y">string_view</span><span style=3D"color: #660;" class=3D"styled-by-pretti=
fy">{</span><span style=3D"color: #080;" class=3D"styled-by-prettify">"=
;hello"</span><span style=3D"color: #660;" class=3D"styled-by-prettify=
">});</span></div></code></div><div><br></div><div>It is done via generic l=
ookup functions which are enabled if a compare function is transparent. Unf=
ortunately, there are now such functions for unordered containers.</div><di=
v><br></div><div>I've found a proposal for fixing this <a href=3D"http:=
//www.open-std.org/jtc1/sc22/wg21/docs/papers/2013/n3573.html">http://www.o=
pen-std.org/jtc1/sc22/wg21/docs/papers/2013/n3573.html</a></div><div>But it=
's rather old and I don't like it for several reasons. I believe th=
e C++ committee dislikes it too)</div><div><br></div><div>1) It proposes he=
terogeneous hash function which forwards type T as std::decay<T>. I c=
onsider this a bad practice because std::decay can destroy initial type (re=
member array-to-pointer conversion).</div><div><br></div><div>2) Heterogene=
ous lookup is enabled by default</div><div class=3D"prettyprint" style=3D"b=
ackground-color: rgb(250, 250, 250); border-color: rgb(187, 187, 187); bord=
er-style: solid; border-width: 1px; word-wrap: break-word;"><code class=3D"=
prettyprint"><div class=3D"subprettyprint"><span style=3D"color: #008;" cla=
ss=3D"styled-by-prettify">template</span><span style=3D"color: #660;" class=
=3D"styled-by-prettify"><</span><span style=3D"color: #008;" class=3D"st=
yled-by-prettify">typename</span><span style=3D"color: #000;" class=3D"styl=
ed-by-prettify"> T</span><span style=3D"color: #660;" class=3D"styled-by-pr=
ettify">,</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> =
</span><span style=3D"color: #008;" class=3D"styled-by-prettify">typename</=
span><span style=3D"color: #000;" class=3D"styled-by-prettify"> </span><spa=
n style=3D"color: #606;" class=3D"styled-by-prettify">Hash</span><span styl=
e=3D"color: #000;" class=3D"styled-by-prettify"> </span><span style=3D"colo=
r: #660;" class=3D"styled-by-prettify">=3D</span><span style=3D"color: #000=
;" class=3D"styled-by-prettify"> std</span><span style=3D"color: #660;" cla=
ss=3D"styled-by-prettify">::</span><span style=3D"color: #000;" class=3D"st=
yled-by-prettify">hash</span><span style=3D"color: #660;" class=3D"styled-b=
y-prettify"><>,</span><span style=3D"color: #000;" class=3D"styled-by=
-prettify"> </span><span style=3D"color: #008;" class=3D"styled-by-prettify=
">typename</span><span style=3D"color: #000;" class=3D"styled-by-prettify">=
</span><span style=3D"color: #606;" class=3D"styled-by-prettify">Eq</span>=
<span style=3D"color: #000;" class=3D"styled-by-prettify"> </span><span sty=
le=3D"color: #660;" class=3D"styled-by-prettify">=3D</span><span style=3D"c=
olor: #000;" class=3D"styled-by-prettify"> std</span><span style=3D"color: =
#660;" class=3D"styled-by-prettify">::</span><span style=3D"color: #000;" c=
lass=3D"styled-by-prettify">equal_to</span><span style=3D"color: #660;" cla=
ss=3D"styled-by-prettify"><>></span><span style=3D"color: #000;" c=
lass=3D"styled-by-prettify"><br>iterator find</span><span style=3D"color: #=
660;" class=3D"styled-by-prettify">(</span><span style=3D"color: #000;" cla=
ss=3D"styled-by-prettify">T t</span><span style=3D"color: #660;" class=3D"s=
tyled-by-prettify">,</span><span style=3D"color: #000;" class=3D"styled-by-=
prettify"> </span><span style=3D"color: #606;" class=3D"styled-by-prettify"=
>Hash</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> h </=
span><span style=3D"color: #660;" class=3D"styled-by-prettify">=3D</span><s=
pan style=3D"color: #000;" class=3D"styled-by-prettify"> </span><span style=
=3D"color: #606;" class=3D"styled-by-prettify">Hash</span><span style=3D"co=
lor: #660;" class=3D"styled-by-prettify">(),</span><span style=3D"color: #0=
00;" class=3D"styled-by-prettify"> </span><span style=3D"color: #606;" clas=
s=3D"styled-by-prettify">Eq</span><span style=3D"color: #000;" class=3D"sty=
led-by-prettify"> e </span><span style=3D"color: #660;" class=3D"styled-by-=
prettify">=3D</span><span style=3D"color: #000;" class=3D"styled-by-prettif=
y"> </span><span style=3D"color: #606;" class=3D"styled-by-prettify">Eq</sp=
an><span style=3D"color: #660;" class=3D"styled-by-prettify">());</span></d=
iv></code></div><div><br></div><div>That's wrong and breaks an old code=
</div><div><div class=3D"prettyprint" style=3D"background-color: rgb(250, 2=
50, 250); border-color: rgb(187, 187, 187); border-style: solid; border-wid=
th: 1px; word-wrap: break-word;"><code class=3D"prettyprint"><div class=3D"=
subprettyprint"><span style=3D"color: #000;" class=3D"styled-by-prettify">s=
ome_map</span><span style=3D"color: #660;" class=3D"styled-by-prettify">.</=
span><span style=3D"color: #000;" class=3D"styled-by-prettify">find</span><=
span style=3D"color: #660;" class=3D"styled-by-prettify">({</span><span sty=
le=3D"color: #066;" class=3D"styled-by-prettify">100</span><span style=3D"c=
olor: #660;" class=3D"styled-by-prettify">,</span><span style=3D"color: #00=
0;" class=3D"styled-by-prettify"> </span><span style=3D"color: #080;" class=
=3D"styled-by-prettify">'A'</span><span style=3D"color: #660;" clas=
s=3D"styled-by-prettify">});</span></div></code></div></div><div><br></div>=
<div>Also it makes the functions ugly.</div><div>=C2=A0=C2=A0</div><div>Now=
I work on my own proposal to make heterogeneous lookup in unordered contai=
ners better.=C2=A0</div><div>Instead of implementing std::hash<> via =
std::decay<T> I propose more safe approach</div><div class=3D"prettyp=
rint" style=3D"background-color: rgb(250, 250, 250); border-color: rgb(187,=
187, 187); border-style: solid; border-width: 1px; word-wrap: break-word;"=
><code class=3D"prettyprint"><div class=3D"subprettyprint"><span style=3D"c=
olor: #008;" class=3D"styled-by-prettify">template</span><span style=3D"col=
or: #000;" class=3D"styled-by-prettify"> </span><span style=3D"color: #660;=
" class=3D"styled-by-prettify"><></span><span style=3D"color: #000;" =
class=3D"styled-by-prettify"><br></span><span style=3D"color: #008;" class=
=3D"styled-by-prettify">struct</span><span style=3D"color: #000;" class=3D"=
styled-by-prettify"> hash</span><span style=3D"color: #080;" class=3D"style=
d-by-prettify"><void></span><span style=3D"color: #000;" class=3D"sty=
led-by-prettify"> </span><span style=3D"color: #660;" class=3D"styled-by-pr=
ettify">{</span><span style=3D"color: #000;" class=3D"styled-by-prettify"><=
br>=C2=A0 =C2=A0 </span><span style=3D"color: #008;" class=3D"styled-by-pre=
ttify">template</span><span style=3D"color: #000;" class=3D"styled-by-prett=
ify"> </span><span style=3D"color: #660;" class=3D"styled-by-prettify"><=
</span><span style=3D"color: #008;" class=3D"styled-by-prettify">typename</=
span><span style=3D"color: #000;" class=3D"styled-by-prettify"> T</span><sp=
an style=3D"color: #660;" class=3D"styled-by-prettify">></span><span sty=
le=3D"color: #000;" class=3D"styled-by-prettify"><br>=C2=A0 =C2=A0 size_t <=
/span><span style=3D"color: #008;" class=3D"styled-by-prettify">operator</s=
pan><span style=3D"color: #660;" class=3D"styled-by-prettify">()(</span><sp=
an style=3D"color: #000;" class=3D"styled-by-prettify">T</span><span style=
=3D"color: #660;" class=3D"styled-by-prettify">&&</span><span style=
=3D"color: #000;" class=3D"styled-by-prettify"> v</span><span style=3D"colo=
r: #660;" class=3D"styled-by-prettify">)</span><span style=3D"color: #000;"=
class=3D"styled-by-prettify"> </span><span style=3D"color: #008;" class=3D=
"styled-by-prettify">const</span><span style=3D"color: #000;" class=3D"styl=
ed-by-prettify"> noexcept </span><span style=3D"color: #660;" class=3D"styl=
ed-by-prettify">{</span><span style=3D"color: #000;" class=3D"styled-by-pre=
ttify"><br>=C2=A0 =C2=A0 =C2=A0 =C2=A0 </span><span style=3D"color: #008;" =
class=3D"styled-by-prettify">return</span><span style=3D"color: #000;" clas=
s=3D"styled-by-prettify"> hash</span><span style=3D"color: #660;" class=3D"=
styled-by-prettify"><</span><span style=3D"color: #008;" class=3D"styled=
-by-prettify">typename</span><span style=3D"color: #000;" class=3D"styled-b=
y-prettify"> remove_cv</span><span style=3D"color: #660;" class=3D"styled-b=
y-prettify"><</span><span style=3D"color: #008;" class=3D"styled-by-pret=
tify">typename</span><span style=3D"color: #000;" class=3D"styled-by-pretti=
fy"> remove_reference</span><span style=3D"color: #660;" class=3D"styled-by=
-prettify"><</span><span style=3D"color: #000;" class=3D"styled-by-prett=
ify">T</span><span style=3D"color: #660;" class=3D"styled-by-prettify">>=
::</span><span style=3D"color: #000;" class=3D"styled-by-prettify">type</sp=
an><span style=3D"color: #660;" class=3D"styled-by-prettify">>::</span><=
span style=3D"color: #000;" class=3D"styled-by-prettify">type</span><span s=
tyle=3D"color: #660;" class=3D"styled-by-prettify">>{}(</span><span styl=
e=3D"color: #000;" class=3D"styled-by-prettify">v</span><span style=3D"colo=
r: #660;" class=3D"styled-by-prettify">);</span><span style=3D"color: #000;=
" class=3D"styled-by-prettify"><br>=C2=A0 =C2=A0 </span><span style=3D"colo=
r: #660;" class=3D"styled-by-prettify">}</span><span style=3D"color: #000;"=
class=3D"styled-by-prettify"><br>=C2=A0 =C2=A0 </span><span style=3D"color=
: #008;" class=3D"styled-by-prettify">typedef</span><span style=3D"color: #=
000;" class=3D"styled-by-prettify"> </span><span style=3D"color: #008;" cla=
ss=3D"styled-by-prettify">void</span><span style=3D"color: #000;" class=3D"=
styled-by-prettify"> is_transparent</span><span style=3D"color: #660;" clas=
s=3D"styled-by-prettify">;</span><span style=3D"color: #000;" class=3D"styl=
ed-by-prettify"><br></span><span style=3D"color: #660;" class=3D"styled-by-=
prettify">};</span><span style=3D"color: #000;" class=3D"styled-by-prettify=
"><br><br></span></div></code></div><div><br></div><div>If an unordered con=
tainer is declared with transparent hash then the <b>default</b> compare fu=
nction should be transparent too. It may look like this</div><div class=3D"=
prettyprint" style=3D"background-color: rgb(250, 250, 250); border-color: r=
gb(187, 187, 187); border-style: solid; border-width: 1px; word-wrap: break=
-word;"><code class=3D"prettyprint"><div class=3D"subprettyprint"><span sty=
le=3D"color: #008;" class=3D"styled-by-prettify">template</span><span style=
=3D"color: #000;" class=3D"styled-by-prettify"> </span><span style=3D"color=
: #660;" class=3D"styled-by-prettify"><</span><span style=3D"color: #008=
;" class=3D"styled-by-prettify">class</span><span style=3D"color: #000;" cl=
ass=3D"styled-by-prettify"> _Value</span><span style=3D"color: #660;" class=
=3D"styled-by-prettify">,</span><span style=3D"color: #000;" class=3D"style=
d-by-prettify"> </span><span style=3D"color: #008;" class=3D"styled-by-pret=
tify">class</span><span style=3D"color: #000;" class=3D"styled-by-prettify"=
> _Hash</span><span style=3D"color: #660;" class=3D"styled-by-prettify">>=
;</span><span style=3D"color: #000;" class=3D"styled-by-prettify"><br></spa=
n><span style=3D"color: #008;" class=3D"styled-by-prettify">struct</span><s=
pan style=3D"color: #000;" class=3D"styled-by-prettify"> _default_pred </sp=
an><span style=3D"color: #660;" class=3D"styled-by-prettify">{</span><span =
style=3D"color: #000;" class=3D"styled-by-prettify"><br>=C2=A0 =C2=A0 </spa=
n><span style=3D"color: #008;" class=3D"styled-by-prettify">typedef</span><=
span style=3D"color: #000;" class=3D"styled-by-prettify"> equal_to</span><s=
pan style=3D"color: #660;" class=3D"styled-by-prettify"><</span><span st=
yle=3D"color: #000;" class=3D"styled-by-prettify">_Value</span><span style=
=3D"color: #660;" class=3D"styled-by-prettify">></span><span style=3D"co=
lor: #000;" class=3D"styled-by-prettify"> type</span><span style=3D"color: =
#660;" class=3D"styled-by-prettify">;</span><span style=3D"color: #000;" cl=
ass=3D"styled-by-prettify"><br></span><span style=3D"color: #660;" class=3D=
"styled-by-prettify">};</span><span style=3D"color: #000;" class=3D"styled-=
by-prettify"><br><br></span><span style=3D"color: #008;" class=3D"styled-by=
-prettify">template</span><span style=3D"color: #000;" class=3D"styled-by-p=
rettify"> </span><span style=3D"color: #660;" class=3D"styled-by-prettify">=
<</span><span style=3D"color: #008;" class=3D"styled-by-prettify">class<=
/span><span style=3D"color: #000;" class=3D"styled-by-prettify"> _Value</sp=
an><span style=3D"color: #660;" class=3D"styled-by-prettify">></span><sp=
an style=3D"color: #000;" class=3D"styled-by-prettify"><br></span><span sty=
le=3D"color: #008;" class=3D"styled-by-prettify">struct</span><span style=
=3D"color: #000;" class=3D"styled-by-prettify"> _default_pred</span><span s=
tyle=3D"color: #660;" class=3D"styled-by-prettify"><</span><span style=
=3D"color: #000;" class=3D"styled-by-prettify"> _Value</span><span style=3D=
"color: #660;" class=3D"styled-by-prettify">,</span><span style=3D"color: #=
000;" class=3D"styled-by-prettify"> hash</span><span style=3D"color: #660;"=
class=3D"styled-by-prettify"><></span><span style=3D"color: #000;" c=
lass=3D"styled-by-prettify"> </span><span style=3D"color: #660;" class=3D"s=
tyled-by-prettify">></span><span style=3D"color: #000;" class=3D"styled-=
by-prettify"> </span><span style=3D"color: #660;" class=3D"styled-by-pretti=
fy">{</span><span style=3D"color: #000;" class=3D"styled-by-prettify"><br>=
=C2=A0 =C2=A0 </span><span style=3D"color: #008;" class=3D"styled-by-pretti=
fy">typedef</span><span style=3D"color: #000;" class=3D"styled-by-prettify"=
> equal_to</span><span style=3D"color: #660;" class=3D"styled-by-prettify">=
<></span><span style=3D"color: #000;" class=3D"styled-by-prettify"> t=
ype</span><span style=3D"color: #660;" class=3D"styled-by-prettify">;</span=
><span style=3D"color: #000;" class=3D"styled-by-prettify"><br></span><span=
style=3D"color: #660;" class=3D"styled-by-prettify">};</span><span style=
=3D"color: #000;" class=3D"styled-by-prettify"><br><br></span><span style=
=3D"color: #008;" class=3D"styled-by-prettify">template</span><span style=
=3D"color: #000;" class=3D"styled-by-prettify"> </span><span style=3D"color=
: #660;" class=3D"styled-by-prettify"><</span><span style=3D"color: #008=
;" class=3D"styled-by-prettify">class</span><span style=3D"color: #000;" cl=
ass=3D"styled-by-prettify"> _Value</span><span style=3D"color: #660;" class=
=3D"styled-by-prettify">,</span><span style=3D"color: #000;" class=3D"style=
d-by-prettify"> </span><span style=3D"color: #008;" class=3D"styled-by-pret=
tify">class</span><span style=3D"color: #000;" class=3D"styled-by-prettify"=
> _Hash </span><span style=3D"color: #660;" class=3D"styled-by-prettify">=
=3D</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> hash</=
span><span style=3D"color: #660;" class=3D"styled-by-prettify"><</span><=
span style=3D"color: #000;" class=3D"styled-by-prettify">_Value</span><span=
style=3D"color: #660;" class=3D"styled-by-prettify">>,</span><span styl=
e=3D"color: #000;" class=3D"styled-by-prettify"> <br>=C2=A0 =C2=A0 =C2=A0 =
=C2=A0 =C2=A0 </span><span style=3D"color: #008;" class=3D"styled-by-pretti=
fy">class</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> =
_Pred </span><span style=3D"color: #660;" class=3D"styled-by-prettify">=3D<=
/span><span style=3D"color: #000;" class=3D"styled-by-prettify"> </span><sp=
an style=3D"color: #008;" class=3D"styled-by-prettify">typename</span><span=
style=3D"color: #000;" class=3D"styled-by-prettify"> _default_pred</span><=
span style=3D"color: #660;" class=3D"styled-by-prettify"><</span><span s=
tyle=3D"color: #000;" class=3D"styled-by-prettify">_Value</span><span style=
=3D"color: #660;" class=3D"styled-by-prettify">,</span><span style=3D"color=
: #000;" class=3D"styled-by-prettify"> _Hash</span><span style=3D"color: #6=
60;" class=3D"styled-by-prettify">>::</span><span style=3D"color: #000;"=
class=3D"styled-by-prettify">type</span><span style=3D"color: #660;" class=
=3D"styled-by-prettify">,</span><span style=3D"color: #000;" class=3D"style=
d-by-prettify"><br>=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 </span><span style=3D=
"color: #008;" class=3D"styled-by-prettify">class</span><span style=3D"colo=
r: #000;" class=3D"styled-by-prettify"> _Alloc </span><span style=3D"color:=
#660;" class=3D"styled-by-prettify">=3D</span><span style=3D"color: #000;"=
class=3D"styled-by-prettify"> allocator</span><span style=3D"color: #660;"=
class=3D"styled-by-prettify"><</span><span style=3D"color: #000;" class=
=3D"styled-by-prettify">_Value</span><span style=3D"color: #660;" class=3D"=
styled-by-prettify">></span><span style=3D"color: #000;" class=3D"styled=
-by-prettify"> </span><span style=3D"color: #660;" class=3D"styled-by-prett=
ify">></span><span style=3D"color: #000;" class=3D"styled-by-prettify"><=
br></span><span style=3D"color: #008;" class=3D"styled-by-prettify">class</=
span><span style=3D"color: #000;" class=3D"styled-by-prettify"> =C2=A0unord=
ered_set</span></div></code></div><div><br></div><div>Then the heterogeneou=
s lookup functions may be enabled via SFINAE if the hash and compare functi=
ons are both transparent.</div><div class=3D"prettyprint" style=3D"backgrou=
nd-color: rgb(250, 250, 250); border-color: rgb(187, 187, 187); border-styl=
e: solid; border-width: 1px; word-wrap: break-word;"><code class=3D"prettyp=
rint"><div class=3D"subprettyprint"><span style=3D"color: #008;" class=3D"s=
tyled-by-prettify">template</span><span style=3D"color: #000;" class=3D"sty=
led-by-prettify"> </span><span style=3D"color: #660;" class=3D"styled-by-pr=
ettify"><</span><span style=3D"color: #008;" class=3D"styled-by-prettify=
">class</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> _K=
2</span><span style=3D"color: #660;" class=3D"styled-by-prettify">,</span><=
span style=3D"color: #000;" class=3D"styled-by-prettify"> </span><span styl=
e=3D"color: #008;" class=3D"styled-by-prettify">class</span><span style=3D"=
color: #000;" class=3D"styled-by-prettify"> _Rt</span><span style=3D"color:=
#660;" class=3D"styled-by-prettify">></span><span style=3D"color: #000;=
" class=3D"styled-by-prettify"><br></span><span style=3D"color: #008;" clas=
s=3D"styled-by-prettify">using</span><span style=3D"color: #000;" class=3D"=
styled-by-prettify"> __enable_if_transparent </span><span style=3D"color: #=
660;" class=3D"styled-by-prettify">=3D</span><span style=3D"color: #000;" c=
lass=3D"styled-by-prettify"> </span><span style=3D"color: #008;" class=3D"s=
tyled-by-prettify">typename</span><span style=3D"color: #000;" class=3D"sty=
led-by-prettify"> enable_if</span><span style=3D"color: #660;" class=3D"sty=
led-by-prettify"><</span><span style=3D"color: #000;" class=3D"styled-by=
-prettify"><br>=C2=A0 =C2=A0 __is_transparent</span><span style=3D"color: #=
660;" class=3D"styled-by-prettify"><</span><span style=3D"color: #000;" =
class=3D"styled-by-prettify">_Hash</span><span style=3D"color: #660;" class=
=3D"styled-by-prettify">,</span><span style=3D"color: #000;" class=3D"style=
d-by-prettify"> _K2</span><span style=3D"color: #660;" class=3D"styled-by-p=
rettify">>::</span><span style=3D"color: #000;" class=3D"styled-by-prett=
ify">value </span><span style=3D"color: #660;" class=3D"styled-by-prettify"=
>&&</span><span style=3D"color: #000;" class=3D"styled-by-prettify"=
><br>=C2=A0 =C2=A0 __is_transparent</span><span style=3D"color: #660;" clas=
s=3D"styled-by-prettify"><</span><span style=3D"color: #000;" class=3D"s=
tyled-by-prettify">_Pred</span><span style=3D"color: #660;" class=3D"styled=
-by-prettify">,</span><span style=3D"color: #000;" class=3D"styled-by-prett=
ify"> _K2</span><span style=3D"color: #660;" class=3D"styled-by-prettify">&=
gt;::</span><span style=3D"color: #000;" class=3D"styled-by-prettify">value=
</span><span style=3D"color: #660;" class=3D"styled-by-prettify">,</span><s=
pan style=3D"color: #000;" class=3D"styled-by-prettify"> _Rt</span><span st=
yle=3D"color: #660;" class=3D"styled-by-prettify">>::</span><span style=
=3D"color: #000;" class=3D"styled-by-prettify">type</span><span style=3D"co=
lor: #660;" class=3D"styled-by-prettify">;</span><span style=3D"color: #000=
;" class=3D"styled-by-prettify"><br>=C2=A0 =C2=A0 <br></span><span style=3D=
"color: #008;" class=3D"styled-by-prettify">template</span><span style=3D"c=
olor: #000;" class=3D"styled-by-prettify"> </span><span style=3D"color: #66=
0;" class=3D"styled-by-prettify"><</span><span style=3D"color: #008;" cl=
ass=3D"styled-by-prettify">class</span><span style=3D"color: #000;" class=
=3D"styled-by-prettify"> _K2</span><span style=3D"color: #660;" class=3D"st=
yled-by-prettify">></span><span style=3D"color: #000;" class=3D"styled-b=
y-prettify"><br>__enable_if_transparent</span><span style=3D"color: #660;" =
class=3D"styled-by-prettify"><</span><span style=3D"color: #000;" class=
=3D"styled-by-prettify">_K2</span><span style=3D"color: #660;" class=3D"sty=
led-by-prettify">,</span><span style=3D"color: #000;" class=3D"styled-by-pr=
ettify"> iterator</span><span style=3D"color: #660;" class=3D"styled-by-pre=
ttify">></span><span style=3D"color: #000;" class=3D"styled-by-prettify"=
> find</span><span style=3D"color: #660;" class=3D"styled-by-prettify">(</s=
pan><span style=3D"color: #008;" class=3D"styled-by-prettify">const</span><=
span style=3D"color: #000;" class=3D"styled-by-prettify"> _K2</span><span s=
tyle=3D"color: #660;" class=3D"styled-by-prettify">&</span><span style=
=3D"color: #000;" class=3D"styled-by-prettify"> __k</span><span style=3D"co=
lor: #660;" class=3D"styled-by-prettify">);</span><span style=3D"color: #00=
0;" class=3D"styled-by-prettify"><br></span></div></code></div><div><br></d=
iv><div>I have implemented this for std::unordered_set in libc++ <a href=3D=
"https://github.com/compmaniak/libcxx/pull/1/files">https://github.com/comp=
maniak/libcxx/pull/1/files</a></div><div>The solution is the same for unord=
ered set/multiset/map/multimap.</div><div><br></div><div>What do you think =
about all of this? Any thoughts would be appreciated.</div><div>Or maybe so=
mebody has already done it better.</div><div><br></div><div>Thanks,</div></=
div>
<p></p>
-- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals" group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
To view this discussion on the web visit <a href=3D"https://groups.google.c=
om/a/isocpp.org/d/msgid/std-proposals/aba58f0f-6180-49a7-bf87-8f2a881666cc%=
40isocpp.org?utm_medium=3Demail&utm_source=3Dfooter">https://groups.google.=
com/a/isocpp.org/d/msgid/std-proposals/aba58f0f-6180-49a7-bf87-8f2a881666cc=
%40isocpp.org</a>.<br />
------=_Part_447_1499587926.1491568135991--
------=_Part_446_1554885244.1491568135990--
.
Author: "T. C." <rs2740@gmail.com>
Date: Sat, 8 Apr 2017 10:51:13 -0700 (PDT)
Raw View
------=_Part_898_1041844511.1491673873628
Content-Type: multipart/alternative;
boundary="----=_Part_899_851106045.1491673873629"
------=_Part_899_851106045.1491673873629
Content-Type: text/plain; charset=UTF-8
On Friday, April 7, 2017 at 8:28:56 AM UTC-4, Roman Orlov wrote:
>
>
> If an unordered container is declared with transparent hash then the
> *default* compare function should be transparent too. It may look like
> this
> template <class _Value, class _Hash>
> struct _default_pred {
> typedef equal_to<_Value> type;
> };
>
> template <class _Value>
> struct _default_pred< _Value, hash<> > {
> typedef equal_to<> type;
> };
>
> template <class _Value, class _Hash = hash<_Value>,
> class _Pred = typename _default_pred<_Value, _Hash>::type,
> class _Alloc = allocator<_Value> >
> class unordered_set
>
This has all the same ABI-breaking problems as default_order.
--
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
To view this discussion on the web visit https://groups.google.com/a/isocpp.org/d/msgid/std-proposals/d03c4b31-33cb-4f7e-bd6b-b6a25a94a3e7%40isocpp.org.
------=_Part_899_851106045.1491673873629
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr"><br><br>On Friday, April 7, 2017 at 8:28:56 AM UTC-4, Roma=
n Orlov wrote:<blockquote class=3D"gmail_quote" style=3D"margin: 0;margin-l=
eft: 0.8ex;border-left: 1px #ccc solid;padding-left: 1ex;"><div dir=3D"ltr"=
><div><br></div><div>If an unordered container is declared with transparent=
hash then the <b>default</b> compare function should be transparent too. I=
t may look like this</div><div style=3D"background-color:rgb(250,250,250);b=
order-color:rgb(187,187,187);border-style:solid;border-width:1px;word-wrap:=
break-word"><code><div><span style=3D"color:#008">template</span><span styl=
e=3D"color:#000"> </span><span style=3D"color:#660"><</span><span style=
=3D"color:#008">class</span><span style=3D"color:#000"> _Value</span><span =
style=3D"color:#660">,</span><span style=3D"color:#000"> </span><span style=
=3D"color:#008">class</span><span style=3D"color:#000"> _Hash</span><span s=
tyle=3D"color:#660">></span><span style=3D"color:#000"><br></span><span =
style=3D"color:#008">struct</span><span style=3D"color:#000"> _default_pred=
</span><span style=3D"color:#660">{</span><span style=3D"color:#000"><br>=
=C2=A0 =C2=A0 </span><span style=3D"color:#008">typedef</span><span style=
=3D"color:#000"> equal_to</span><span style=3D"color:#660"><</span><span=
style=3D"color:#000">_Value</span><span style=3D"color:#660">></span><s=
pan style=3D"color:#000"> type</span><span style=3D"color:#660">;</span><sp=
an style=3D"color:#000"><br></span><span style=3D"color:#660">};</span><spa=
n style=3D"color:#000"><br><br></span><span style=3D"color:#008">template</=
span><span style=3D"color:#000"> </span><span style=3D"color:#660"><</sp=
an><span style=3D"color:#008">class</span><span style=3D"color:#000"> _Valu=
e</span><span style=3D"color:#660">></span><span style=3D"color:#000"><b=
r></span><span style=3D"color:#008">struct</span><span style=3D"color:#000"=
> _default_pred</span><span style=3D"color:#660"><</span><span style=3D"=
color:#000"> _Value</span><span style=3D"color:#660">,</span><span style=3D=
"color:#000"> hash</span><span style=3D"color:#660"><></span><span st=
yle=3D"color:#000"> </span><span style=3D"color:#660">></span><span styl=
e=3D"color:#000"> </span><span style=3D"color:#660">{</span><span style=3D"=
color:#000"><br>=C2=A0 =C2=A0 </span><span style=3D"color:#008">typedef</sp=
an><span style=3D"color:#000"> equal_to</span><span style=3D"color:#660">&l=
t;></span><span style=3D"color:#000"> type</span><span style=3D"color:#6=
60">;</span><span style=3D"color:#000"><br></span><span style=3D"color:#660=
">};</span><span style=3D"color:#000"><br><br></span><span style=3D"color:#=
008">template</span><span style=3D"color:#000"> </span><span style=3D"color=
:#660"><</span><span style=3D"color:#008">class</span><span style=3D"col=
or:#000"> _Value</span><span style=3D"color:#660">,</span><span style=3D"co=
lor:#000"> </span><span style=3D"color:#008">class</span><span style=3D"col=
or:#000"> _Hash </span><span style=3D"color:#660">=3D</span><span style=3D"=
color:#000"> hash</span><span style=3D"color:#660"><</span><span style=
=3D"color:#000">_Value</span><span style=3D"color:#660">>,</span><span s=
tyle=3D"color:#000"> <br>=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 </span><span st=
yle=3D"color:#008">class</span><span style=3D"color:#000"> _Pred </span><sp=
an style=3D"color:#660">=3D</span><span style=3D"color:#000"> </span><span =
style=3D"color:#008">typename</span><span style=3D"color:#000"> _default_pr=
ed</span><span style=3D"color:#660"><</span><span style=3D"color:#000">_=
Value</span><span style=3D"color:#660">,</span><span style=3D"color:#000"> =
_Hash</span><span style=3D"color:#660">>::</span><span style=3D"color:#0=
00">type</span><span style=3D"color:#660">,</span><span style=3D"color:#000=
"><br>=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 </span><span style=3D"color:#008">=
class</span><span style=3D"color:#000"> _Alloc </span><span style=3D"color:=
#660">=3D</span><span style=3D"color:#000"> allocator</span><span style=3D"=
color:#660"><</span><span style=3D"color:#000">_Value</span><span style=
=3D"color:#660">></span><span style=3D"color:#000"> </span><span style=
=3D"color:#660">></span><span style=3D"color:#000"><br></span><span styl=
e=3D"color:#008">class</span><span style=3D"color:#000"> =C2=A0unordered_se=
t</span></div></code></div></div></blockquote><div><br></div><div>This has =
all the same ABI-breaking problems as default_order.=C2=A0</div></div>
<p></p>
-- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals" group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
To view this discussion on the web visit <a href=3D"https://groups.google.c=
om/a/isocpp.org/d/msgid/std-proposals/d03c4b31-33cb-4f7e-bd6b-b6a25a94a3e7%=
40isocpp.org?utm_medium=3Demail&utm_source=3Dfooter">https://groups.google.=
com/a/isocpp.org/d/msgid/std-proposals/d03c4b31-33cb-4f7e-bd6b-b6a25a94a3e7=
%40isocpp.org</a>.<br />
------=_Part_899_851106045.1491673873629--
------=_Part_898_1041844511.1491673873628--
.
Author: Roman Orlov <mr.gordon.freman@gmail.com>
Date: Sat, 8 Apr 2017 12:15:37 -0700 (PDT)
Raw View
------=_Part_1223_279487776.1491678937730
Content-Type: multipart/alternative;
boundary="----=_Part_1224_57399921.1491678937730"
------=_Part_1224_57399921.1491678937730
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: quoted-printable
=D1=81=D1=83=D0=B1=D0=B1=D0=BE=D1=82=D0=B0, 8 =D0=B0=D0=BF=D1=80=D0=B5=D0=
=BB=D1=8F 2017 =D0=B3., 20:51:13 UTC+3 =D0=BF=D0=BE=D0=BB=D1=8C=D0=B7=D0=BE=
=D0=B2=D0=B0=D1=82=D0=B5=D0=BB=D1=8C T. C. =D0=BD=D0=B0=D0=BF=D0=B8=D1=81=
=D0=B0=D0=BB:
>
>
> On Friday, April 7, 2017 at 8:28:56 AM UTC-4, Roman Orlov wrote:
>>
>>
>> If an unordered container is declared with transparent hash then the=20
>> *default* compare function should be transparent too. It may look like=
=20
>> this
>> template <class _Value, class _Hash>
>> struct _default_pred {
>> typedef equal_to<_Value> type;
>> };
>>
>> template <class _Value>
>> struct _default_pred< _Value, hash<> > {
>> typedef equal_to<> type;
>> };
>>
>> template <class _Value, class _Hash =3D hash<_Value>,=20
>> class _Pred =3D typename _default_pred<_Value, _Hash>::type,
>> class _Alloc =3D allocator<_Value> >
>> class unordered_set
>>
>
> This has all the same ABI-breaking problems as default_order.=20
>
=20
Could you show the code that will be broken?
Consider the simple case when only Value template parameter is defined
std::unordered_set<std::string> s;
The code will work because the hash function is std::hash<std::string> and=
=20
compare function is std::equal_to<std::string>
The code will work if a custom hash function is provided
std::unordered_set<std::string, &my_hash_func> s;
In this case the compare function is still std::equal_to<std::string>.
ABI might be broken in the following code
std::unordered_set<std::string, std::hash<>> s;
In this case the compare function will be std::equal_to<> instead of=20
std::equal_to<std::string>. But std::hash<> is not a valid hash function=20
until this proposal.
--=20
You received this message because you are subscribed to the Google Groups "=
ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
To view this discussion on the web visit https://groups.google.com/a/isocpp=
..org/d/msgid/std-proposals/636a5eb5-3a8d-4196-84cc-f56fe0a4a383%40isocpp.or=
g.
------=_Part_1224_57399921.1491678937730
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr"><div>=D1=81=D1=83=D0=B1=D0=B1=D0=BE=D1=82=D0=B0, 8 =D0=B0=
=D0=BF=D1=80=D0=B5=D0=BB=D1=8F 2017 =D0=B3., 20:51:13 UTC+3 =D0=BF=D0=BE=D0=
=BB=D1=8C=D0=B7=D0=BE=D0=B2=D0=B0=D1=82=D0=B5=D0=BB=D1=8C T. C. =D0=BD=D0=
=B0=D0=BF=D0=B8=D1=81=D0=B0=D0=BB:<blockquote class=3D"gmail_quote" style=
=3D"margin: 0px 0px 0px 0.8ex; border-left: 1px solid rgb(204, 204, 204); p=
adding-left: 1ex;"><div dir=3D"ltr"><br>On Friday, April 7, 2017 at 8:28:56=
AM UTC-4, Roman Orlov wrote:<blockquote class=3D"gmail_quote" style=3D"mar=
gin: 0px 0px 0px 0.8ex; border-left: 1px solid rgb(204, 204, 204); padding-=
left: 1ex;"><div dir=3D"ltr"><div><br></div><div>If an unordered container =
is declared with transparent hash then the=C2=A0<b>default</b>=C2=A0compare=
function should be transparent too. It may look like this</div><div style=
=3D"border-width: 1px; border-style: solid; border-color: rgb(187, 187, 187=
); background-color: rgb(250, 250, 250); word-wrap: break-word;"><code><spa=
n style=3D"color: rgb(0, 0, 136);">template</span><span style=3D"color: rgb=
(0, 0, 0);">=C2=A0</span><span style=3D"color: rgb(102, 102, 0);"><</spa=
n><span style=3D"color: rgb(0, 0, 136);">class</span><span style=3D"color: =
rgb(0, 0, 0);">=C2=A0_Value</span><span style=3D"color: rgb(102, 102, 0);">=
,</span><span style=3D"color: rgb(0, 0, 0);">=C2=A0</span><span style=3D"co=
lor: rgb(0, 0, 136);">class</span><span style=3D"color: rgb(0, 0, 0);">=C2=
=A0_Hash</span><span style=3D"color: rgb(102, 102, 0);">></span><span st=
yle=3D"color: rgb(0, 0, 0);"><br></span><span style=3D"color: rgb(0, 0, 136=
);">struct</span><span style=3D"color: rgb(0, 0, 0);">=C2=A0_default_pred=
=C2=A0</span><span style=3D"color: rgb(102, 102, 0);">{</span><span style=
=3D"color: rgb(0, 0, 0);"><br>=C2=A0 =C2=A0=C2=A0</span><span style=3D"colo=
r: rgb(0, 0, 136);">typedef</span><span style=3D"color: rgb(0, 0, 0);">=C2=
=A0equal_to</span><span style=3D"color: rgb(102, 102, 0);"><</span><span=
style=3D"color: rgb(0, 0, 0);">_Value</span><span style=3D"color: rgb(102,=
102, 0);">></span><span style=3D"color: rgb(0, 0, 0);">=C2=A0type</span=
><span style=3D"color: rgb(102, 102, 0);">;</span><span style=3D"color: rgb=
(0, 0, 0);"><br></span><span style=3D"color: rgb(102, 102, 0);">};</span><s=
pan style=3D"color: rgb(0, 0, 0);"><br><br></span><span style=3D"color: rgb=
(0, 0, 136);">template</span><span style=3D"color: rgb(0, 0, 0);">=C2=A0</s=
pan><span style=3D"color: rgb(102, 102, 0);"><</span><span style=3D"colo=
r: rgb(0, 0, 136);">class</span><span style=3D"color: rgb(0, 0, 0);">=C2=A0=
_Value</span><span style=3D"color: rgb(102, 102, 0);">></span><span styl=
e=3D"color: rgb(0, 0, 0);"><br></span><span style=3D"color: rgb(0, 0, 136);=
">struct</span><span style=3D"color: rgb(0, 0, 0);">=C2=A0_default_pred</sp=
an><span style=3D"color: rgb(102, 102, 0);"><</span><span style=3D"color=
: rgb(0, 0, 0);">=C2=A0_Value</span><span style=3D"color: rgb(102, 102, 0);=
">,</span><span style=3D"color: rgb(0, 0, 0);">=C2=A0hash</span><span style=
=3D"color: rgb(102, 102, 0);"><></span><span style=3D"color: rgb(0, 0=
, 0);">=C2=A0</span><span style=3D"color: rgb(102, 102, 0);">></span><sp=
an style=3D"color: rgb(0, 0, 0);">=C2=A0</span><span style=3D"color: rgb(10=
2, 102, 0);">{</span><span style=3D"color: rgb(0, 0, 0);"><br>=C2=A0 =C2=A0=
=C2=A0</span><span style=3D"color: rgb(0, 0, 136);">typedef</span><span sty=
le=3D"color: rgb(0, 0, 0);">=C2=A0equal_to</span><span style=3D"color: rgb(=
102, 102, 0);"><></span><span style=3D"color: rgb(0, 0, 0);">=C2=A0ty=
pe</span><span style=3D"color: rgb(102, 102, 0);">;</span><span style=3D"co=
lor: rgb(0, 0, 0);"><br></span><span style=3D"color: rgb(102, 102, 0);">};<=
/span><span style=3D"color: rgb(0, 0, 0);"><br><br></span><span style=3D"co=
lor: rgb(0, 0, 136);">template</span><span style=3D"color: rgb(0, 0, 0);">=
=C2=A0</span><span style=3D"color: rgb(102, 102, 0);"><</span><span styl=
e=3D"color: rgb(0, 0, 136);">class</span><span style=3D"color: rgb(0, 0, 0)=
;">=C2=A0_Value</span><span style=3D"color: rgb(102, 102, 0);">,</span><spa=
n style=3D"color: rgb(0, 0, 0);">=C2=A0</span><span style=3D"color: rgb(0, =
0, 136);">class</span><span style=3D"color: rgb(0, 0, 0);">=C2=A0_Hash=C2=
=A0</span><span style=3D"color: rgb(102, 102, 0);">=3D</span><span style=3D=
"color: rgb(0, 0, 0);">=C2=A0hash</span><span style=3D"color: rgb(102, 102,=
0);"><</span><span style=3D"color: rgb(0, 0, 0);">_Value</span><span st=
yle=3D"color: rgb(102, 102, 0);">>,</span><span style=3D"color: rgb(0, 0=
, 0);">=C2=A0<br>=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0=C2=A0</span><span style=
=3D"color: rgb(0, 0, 136);">class</span><span style=3D"color: rgb(0, 0, 0);=
">=C2=A0_Pred=C2=A0</span><span style=3D"color: rgb(102, 102, 0);">=3D</spa=
n><span style=3D"color: rgb(0, 0, 0);">=C2=A0</span><span style=3D"color: r=
gb(0, 0, 136);">typename</span><span style=3D"color: rgb(0, 0, 0);">=C2=A0_=
default_pred</span><span style=3D"color: rgb(102, 102, 0);"><</span><spa=
n style=3D"color: rgb(0, 0, 0);">_Value</span><span style=3D"color: rgb(102=
, 102, 0);">,</span><span style=3D"color: rgb(0, 0, 0);">=C2=A0_Hash</span>=
<span style=3D"color: rgb(102, 102, 0);">>::</span><span style=3D"color:=
rgb(0, 0, 0);">type</span><span style=3D"color: rgb(102, 102, 0);">,</span=
><span style=3D"color: rgb(0, 0, 0);"><br>=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=
=A0=C2=A0</span><span style=3D"color: rgb(0, 0, 136);">class</span><span st=
yle=3D"color: rgb(0, 0, 0);">=C2=A0_Alloc=C2=A0</span><span style=3D"color:=
rgb(102, 102, 0);">=3D</span><span style=3D"color: rgb(0, 0, 0);">=C2=A0al=
locator</span><span style=3D"color: rgb(102, 102, 0);"><</span><span sty=
le=3D"color: rgb(0, 0, 0);">_Value</span><span style=3D"color: rgb(102, 102=
, 0);">></span><span style=3D"color: rgb(0, 0, 0);">=C2=A0</span><span s=
tyle=3D"color: rgb(102, 102, 0);">></span><span style=3D"color: rgb(0, 0=
, 0);"><br></span><span style=3D"color: rgb(0, 0, 136);">class</span><span =
style=3D"color: rgb(0, 0, 0);">=C2=A0=C2=A0unordered_set</span></code></div=
></div></blockquote><div><br></div><div>This has all the same ABI-breaking =
problems as default_order.=C2=A0</div></div></blockquote><div>=C2=A0</div><=
/div>Could you show the code that will be broken?<div><br><div>Consider the=
simple case when only Value template parameter is defined</div></div><div>=
<div class=3D"prettyprint" style=3D"background-color: rgb(250, 250, 250); b=
order-color: rgb(187, 187, 187); border-style: solid; border-width: 1px; wo=
rd-wrap: break-word;"><code class=3D"prettyprint"><div class=3D"subprettypr=
int"><span style=3D"color: #000;" class=3D"styled-by-prettify">std</span><s=
pan style=3D"color: #660;" class=3D"styled-by-prettify">::</span><span styl=
e=3D"color: #000;" class=3D"styled-by-prettify">unordered_set</span><span s=
tyle=3D"color: #660;" class=3D"styled-by-prettify"><</span><span style=
=3D"color: #000;" class=3D"styled-by-prettify">std</span><span style=3D"col=
or: #660;" class=3D"styled-by-prettify">::</span><span style=3D"color: #008=
;" class=3D"styled-by-prettify">string</span><span style=3D"color: #660;" c=
lass=3D"styled-by-prettify">></span><span style=3D"color: #000;" class=
=3D"styled-by-prettify"> s</span><span style=3D"color: #660;" class=3D"styl=
ed-by-prettify">;</span></div></code></div></div><div>The code will work be=
cause the hash function is std::hash<std::string> and compare functio=
n is std::equal_to<std::string></div><div><br></div><div>The code wil=
l work if a custom hash function is provided</div><div><div class=3D"pretty=
print" style=3D"background-color: rgb(250, 250, 250); border-color: rgb(187=
, 187, 187); border-style: solid; border-width: 1px; word-wrap: break-word;=
"><code class=3D"prettyprint"><div class=3D"subprettyprint"><span style=3D"=
color: #000;" class=3D"styled-by-prettify">std</span><span style=3D"color: =
#660;" class=3D"styled-by-prettify">::</span><span style=3D"color: #000;" c=
lass=3D"styled-by-prettify">unordered_set</span><span style=3D"color: #660;=
" class=3D"styled-by-prettify"><</span><span style=3D"color: #000;" clas=
s=3D"styled-by-prettify">std</span><span style=3D"color: #660;" class=3D"st=
yled-by-prettify">::</span><span style=3D"color: #008;" class=3D"styled-by-=
prettify">string</span><span style=3D"color: #660;" class=3D"styled-by-pret=
tify">,</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> </=
span><span style=3D"color: #660;" class=3D"styled-by-prettify">&</span>=
<span style=3D"color: #000;" class=3D"styled-by-prettify">my_hash_func</spa=
n><span style=3D"color: #660;" class=3D"styled-by-prettify">></span><spa=
n style=3D"color: #000;" class=3D"styled-by-prettify"> s</span><span style=
=3D"color: #660;" class=3D"styled-by-prettify">;</span></div></code></div><=
/div><div>In this case the compare function is still std::equal_to<std::=
string>.</div><div><br></div><div>ABI might be broken in the following c=
ode</div><div><div class=3D"prettyprint" style=3D"background-color: rgb(250=
, 250, 250); border-color: rgb(187, 187, 187); border-style: solid; border-=
width: 1px; word-wrap: break-word;"><code class=3D"prettyprint"><div class=
=3D"subprettyprint"><span style=3D"color: #000;" class=3D"styled-by-prettif=
y">std</span><span style=3D"color: #660;" class=3D"styled-by-prettify">::</=
span><span style=3D"color: #000;" class=3D"styled-by-prettify">unordered_se=
t</span><span style=3D"color: #660;" class=3D"styled-by-prettify"><</spa=
n><span style=3D"color: #000;" class=3D"styled-by-prettify">std</span><span=
style=3D"color: #660;" class=3D"styled-by-prettify">::</span><span style=
=3D"color: #008;" class=3D"styled-by-prettify">string</span><span style=3D"=
color: #660;" class=3D"styled-by-prettify">,</span><span style=3D"color: #0=
00;" class=3D"styled-by-prettify"> std</span><span style=3D"color: #660;" c=
lass=3D"styled-by-prettify">::</span><span style=3D"color: #000;" class=3D"=
styled-by-prettify">hash</span><span style=3D"color: #660;" class=3D"styled=
-by-prettify"><>></span><span style=3D"color: #000;" class=3D"styl=
ed-by-prettify"> s</span><span style=3D"color: #660;" class=3D"styled-by-pr=
ettify">;</span></div></code></div></div><div>In this case the compare func=
tion will be std::equal_to<> instead of std::equal_to<std::string&=
gt;. But std::hash<> is not a valid hash function until this proposal=
..</div><div><br></div><div><br></div></div>
<p></p>
-- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals" group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
To view this discussion on the web visit <a href=3D"https://groups.google.c=
om/a/isocpp.org/d/msgid/std-proposals/636a5eb5-3a8d-4196-84cc-f56fe0a4a383%=
40isocpp.org?utm_medium=3Demail&utm_source=3Dfooter">https://groups.google.=
com/a/isocpp.org/d/msgid/std-proposals/636a5eb5-3a8d-4196-84cc-f56fe0a4a383=
%40isocpp.org</a>.<br />
------=_Part_1224_57399921.1491678937730--
------=_Part_1223_279487776.1491678937730--
.