<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<title>Issue 2215: (unordered) associative container functors should be CopyConstructible</title>
<meta property="og:title" content="Issue 2215: (unordered) associative container functors should be CopyConstructible">
<meta property="og:description" content="C++ library issue. Status: Open">
<meta property="og:url" content="https://cplusplus.github.io/LWG/issue2215.html">
<meta property="og:type" content="website">
<meta property="og:image" content="http://cplusplus.github.io/LWG/images/cpp_logo.png">
<meta property="og:image:alt" content="C++ logo">
<style>
  p {text-align:justify}
  li {text-align:justify}
  pre code.backtick::before { content: "`" }
  pre code.backtick::after { content: "`" }
  blockquote.note
  {
    background-color:#E0E0E0;
    padding-left: 15px;
    padding-right: 15px;
    padding-top: 1px;
    padding-bottom: 1px;
  }
  ins {background-color:#A0FFA0}
  del {background-color:#FFA0A0}
  table.issues-index { border: 1px solid; border-collapse: collapse; }
  table.issues-index th { text-align: center; padding: 4px; border: 1px solid; }
  table.issues-index td { padding: 4px; border: 1px solid; }
  table.issues-index td:nth-child(1) { text-align: right; }
  table.issues-index td:nth-child(2) { text-align: left; }
  table.issues-index td:nth-child(3) { text-align: left; }
  table.issues-index td:nth-child(4) { text-align: left; }
  table.issues-index td:nth-child(5) { text-align: center; }
  table.issues-index td:nth-child(6) { text-align: center; }
  table.issues-index td:nth-child(7) { text-align: left; }
  table.issues-index td:nth-child(5) span.no-pr { color: red; }
  @media (prefers-color-scheme: dark) {
     html {
        color: #ddd;
        background-color: black;
     }
     ins {
        background-color: #225522
     }
     del {
        background-color: #662222
     }
     a {
        color: #6af
     }
     a:visited {
        color: #6af
     }
     blockquote.note
     {
        background-color: rgba(255, 255, 255, .10)
     }
  }
</style>
</head>
<body>
<hr>
<p><em>This page is a snapshot from the LWG issues list, see the <a href="lwg-active.html">Library Active Issues List</a> for more information and the meaning of <a href="lwg-active.html#Open">Open</a> status.</em></p>
<h3 id="2215"><a href="lwg-active.html#2215">2215</a>. (unordered) associative container functors should be <code>CopyConstructible</code></h3>
<p><b>Section:</b> 23.2.7 <a href="https://wg21.link/associative.reqmts">[associative.reqmts]</a>, 23.2.8 <a href="https://wg21.link/unord.req">[unord.req]</a> <b>Status:</b> <a href="lwg-active.html#Open">Open</a>
 <b>Submitter:</b> Alisdair Meredith <b>Opened:</b> 2012-11-14 <b>Last modified:</b> 2015-10-22</p>
<p><b>Priority: </b>3
</p>
<p><b>View other</b> <a href="lwg-index-open.html#associative.reqmts">active issues</a> in [associative.reqmts].</p>
<p><b>View all other</b> <a href="lwg-index.html#associative.reqmts">issues</a> in [associative.reqmts].</p>
<p><b>View all issues with</b> <a href="lwg-status.html#Open">Open</a> status.</p>
<p><b>Discussion:</b></p>
<p>
The requirements on the functors used to arrange elements in the various associative and
unordered containers are given by a set of expressions in tables 102 &mdash; Associative container
requirements, and 103 &mdash; Unordered associative container requirements.  In keeping with Library
convention these expressions make the minimal requirements necessary on their types.  For
example, we have the following 3 row extracts for the unordered containers:
</p>
<table>
<tr>
  <td>
    <b>Expression</b>
  </td>
  <td>
    <b>Assertion/note pre-/post-condition</b>
  </td>
</tr>

<tr>
  <td>
<pre>
<code>X(n, hf, eq)</code>
<code>X a(n, hf, eq)</code>
</pre>
  </td>
  <td>
    <i>Requires:</i> <code>hasher</code> and <code>key_equal</code> are <code>CopyConstructible</code>.
 </td>
</tr>

<tr>
  <td>
<pre>
<code>X(n, hf)</code>
<code>X a(n, hf)</code>
</pre>
  </td>
  <td>
    <i>Requires:</i> <code>hasher</code> is <code>CopyConstructible</code> and 
                  <code>key_equal</code> is <code>DefaultConstructible</code>.
 </td>
</tr>

<tr>
  <td>
<pre>
<code>X(n)</code>
<code>X a(n)</code>
</pre>
  </td>
  <td>
    <i>Requires:</i> <code>hasher</code> and <code>key_equal</code> are <code>DefaultConstructible</code>.
 </td>
</tr>
</table>

<p>
However, the signature for each class template requires that the functors must effectively be
<code>CopyConstructible</code> for each of these expressions:
</p>

<blockquote><pre>
template &lt;class Key,
          class T,
          class Hash  = hash&lt;Key>,
          class Pred  = std::equal_to&lt;Key>,
          class Allocator = std::allocator&lt;std::pair&lt;const Key, T> > >
class unordered_map
{
  <i>...</i>

  <i>// construct/destroy/copy</i>
  explicit unordered_map(size_type n = <i>see below</i>,
                         const hasher&amp; hf = hasher(),
                         const key_equal&amp; eql = key_equal(),
                         const allocator_type&amp; a = allocator_type());

  <i>...</i>
}
</pre></blockquote>

<p>
The letter of the standard can be honored as long as implementors recognize
their freedom to split this one signature into multiple overloads, so that
the documented default arguments (requiring a <code>CopyConstructible</code> functor)
are not actually passed as default arguments.
</p>
<p>
As we look into the requirements for the copy constructor and copy-assignment
operator, the requirements are even more vague, as the explicit requirements on
the functors are not called out, other than saying that the functors are copied.
</p>
<p>
Must the functors be <code>CopyAssignable</code>? Or is <code>CopyConstructible</code>
sufficient in this case?  Do we require that the functors be <code>Swappable</code>
so that the copy-swap idiom can be deployed here?  Note that a type that is both
<code>CopyConstructible</code> and <code>CopyAssignable</code> is still not guaranteed to
be <code>Swappable</code> as the user may delete the <code>swap</code> function for their
type in their own namespace, which would be found via ADL.
</p>
<p>
Some clean-up of the requirements table looks necessary, to at least document the
assignment behavior.  In addition, we should have clear guidance on whether these
functors should always be <code>CopyConstructible</code>, as suggested by the class
template definitions, or if the requirement tables are correct and we should
explicitly split up the constructors in the (unordered) associative containers
to no longer use default (function) arguments to obtain their defaulted functors.
</p>
<p>
I recommend the simplest solution would be to always require that the functors
for (unordered) associative containers be <code>CopyConstructible</code>, above the
requirements tables themselves, so that the issue need not be addressed within
the tables.  I suggest that the assignment operators for these containers add
the requirement that the functors be <code>Swappable</code>, rather than forwarding
the corresponding <code>Assignable</code> requirement.
</p>

<p><i>[2013-03-15 Issues Teleconference]</i></p>

<p>
Moved to Open.
</p>
<p>
Alisdair to propose wording.
</p>

<p><i>[2014-06-08, Daniel comments]</i></p>

<p>
The area of this issue partially overlaps what LWG <a href="lwg-active.html#2227" title="Stateful comparison objects in associative containers (Status: Open)">2227</a><sup><a href="https://cplusplus.github.io/LWG/issue2227" title="Latest snapshot">(i)</a></sup> addresses.
</p>

<p><i>[2015-10-20, Daniel comments]</i></p>

<p>
The revised resolution of LWG <a href="lwg-active.html#2227" title="Stateful comparison objects in associative containers (Status: Open)">2227</a><sup><a href="https://cplusplus.github.io/LWG/issue2227" title="Latest snapshot">(i)</a></sup> should resolve this issue as well. It follows the recommendations
of the submitter to require <code>CopyConstructible</code> requirements for the function objects owned by containers,
but it does not impose any further fundamental requirements.
</p>


<p id="res-2215"><b>Proposed resolution:</b></p>
<p>
See the resolution of LWG <a href="lwg-active.html#2227" title="Stateful comparison objects in associative containers (Status: Open)">2227</a><sup><a href="https://cplusplus.github.io/LWG/issue2227" title="Latest snapshot">(i)</a></sup>.
</p>





</body>
</html>
