<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3c.org/TR/1999/REC-html401-19991224/loose.dtd">
<!-- saved from url=(0047)file://P:\j16\33-pre-oxford\lwg\lwg-active.html -->
<HTML><HEAD><TITLE>C++ Standard Library Active Issues List</TITLE>
<META http-equiv=Content-Type content="text/html; charset=windows-1252">
<META content="MSHTML 6.00.2722.900" name=GENERATOR></HEAD>
<BODY text=#000000 bgColor=#ffffff>
<TABLE>
  <TBODY>
  <TR>
    <TD align=left>Doc. no.</TD>
    <TD align=left>N1440 = 03-0022</TD></TR>
  <TR>
    <TD align=left>Date:</TD>
    <TD align=left>3 Mar 2003</TD></TR>
  <TR>
    <TD align=left>Project:</TD>
    <TD align=left>Programming Language C++</TD></TR>
  <TR>
    <TD align=left>Reply to:</TD>
    <TD align=left>Matt Austern &lt;austern@apple.com&gt;</TD></TR></TBODY></TABLE>
<H1>C++ Standard Library Active Issues List (Revision 25)</H1>
<P>Reference ISO/IEC IS 14882:1998(E)</P>
<P>Also see:</P>
<UL>
  <LI><A href="file:///P:/j16/33-pre-oxford/lwg/lwg-toc.html">Table of 
  Contents</A> for all library issues. 
  <LI><A href="file:///P:/j16/33-pre-oxford/lwg/lwg-index.html">Index by 
  Section</A> for all library issues. 
  <LI><A href="file:///P:/j16/33-pre-oxford/lwg/lwg-status.html">Index by 
  Status</A> for all library issues. 
  <LI><A href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html">Library Defect 
  Reports List</A> 
  <LI><A href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html">Library Closed 
  Issues List</A> </LI></UL>
<P>The purpose of this document is to record the status of issues which have 
come before the Library Working Group (LWG) of the ANSI (J16) and ISO (WG21) C++ 
Standards Committee. Issues represent potential defects in the ISO/IEC IS 
14882:1998(E) document. Issues are not to be used to request new features or 
other extensions. </P>
<P>This document contains only library issues which are actively being 
considered by the Library Working Group. That is, issues which have a status of 
<A href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#New">New</A>, <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>, <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A>, and <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Review">Review</A>. See 
<A href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html">Library Defect 
Reports List</A> for issues considered defects and <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html">Library Closed Issues 
List</A> for issues considered closed.</P>
<P>The issues in these lists are not necessarily formal ISO Defect Reports 
(DR's). While some issues will eventually be elevated to official Defect Report 
status, other issues will be disposed of in other ways. See <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Status">Issue 
Status</A>.</P>
<P>This document is in an experimental format designed for both viewing via a 
world-wide web browser and hard-copy printing. It is available as an HTML file 
for browsing or PDF file for printing.</P>
<P>Prior to Revision 14, library issues lists existed in two slightly different 
versions; a Committee Version and a Public Version. Beginning with Revision 14 
the two versions were combined into a single version.</P>
<P>This document includes <I>[bracketed italicized notes]</I> as a reminder to 
the LWG of current progress on issues. Such notes are strictly unofficial and 
should be read with caution as they may be incomplete or incorrect. Be aware 
that LWG support for a particular resolution can quickly change if new 
viewpoints or killer examples are presented in subsequent discussions.</P>
<P>For the most current official version of this document see <A 
href="http://www.dkuug.dk/jtc1/sc22/wg21">http://www.dkuug.dk/jtc1/sc22/wg21</A>. 
Requests for further information about this document should include the document 
number above, reference ISO/IEC 14882:1998(E), and be submitted to Information 
Technology Industry Council (ITI), 1250 Eye Street NW, Washington, DC 20005.</P>
<P>Public information as to how to obtain a copy of the C++ Standard, join the 
standards committee, submit an issue, or comment on an issue can be found in the 
C++ FAQ at <A 
href="http://www.research.att.com/~austern/csc/faq.html">http://www.research.att.com/~austern/csc/faq.html</A>. 
Public discussion of C++ Standard related issues occurs on <A 
href="news:comp.std.c++">news:comp.std.c++</A>. </P>
<P>For committee members, files available on the committee's private web site 
include the HTML version of the Standard itself. HTML hyperlinks from this 
issues list to those files will only work for committee members who have 
downloaded them into the same disk directory as the issues list files. </P>
<H2>Revision History</H2>
<UL>
  <LI>R25: Pre-Oxford mailing. Added new issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#390">390</A>-<A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#402">402</A>. 
  <LI>R24: Post-Santa Cruz mailing: reflects decisions made at the Santa Cruz 
  meeting. All Ready issues from R23 with the exception of <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#253">253</A>, which has 
  been given a new proposed resolution, were moved to DR status. Added new 
  issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#383">383</A>-<A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#389">389</A>. (Issues 
  <A href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#387">387</A>-<A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#389">389</A> were 
  discussed at the meeting.) Made progress on issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#225">225</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#226">226</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#229">229</A>: <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#225">225</A> and <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#229">229</A> have been 
  moved to Ready status, and the only remaining concerns with <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#226">226</A> involve 
  wording. 
  <LI>R23: Pre-Santa Cruz mailing. Added new issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#367">367</A>-<A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#382">382</A>. Moved 
  issues in the TC to TC status. 
  <LI>R22: Post-Curaao mailing. Added new issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#362">362</A>-<A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#366">366</A>. 
  <LI>R21: Pre-Curaao mailing. Added new issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#351">351</A>-<A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#361">361</A>. 
  <LI>R20: Post-Redmond mailing; reflects actions taken in Redmond. Added new 
  issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#336">336</A>-<A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#350">350</A>, of which 
  issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#347">347</A>-<A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#350">350</A> were added 
  since Redmond, hence not discussed at the meeting. All Ready issues were moved 
  to DR status, with the exception of issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#284">284</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#241">241</A>, and <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#267">267</A>. 
  Noteworthy issues discussed at Redmond include <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#120">120</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#202">202</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#226">226</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#233">233</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#270">270</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#253">253</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#254">254</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#323">323</A>. 
  <LI>R19: Pre-Redmond mailing. Added new issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#323">323</A>-<A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#335">335</A>. 
  <LI>R18: Post-Copenhagen mailing; reflects actions taken in Copenhagen. Added 
  new issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#312">312</A>-<A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#317">317</A>, and 
  discussed new issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#271">271</A>-<A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#314">314</A>. Changed 
  status of issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#103">103</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#118">118</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#136">136</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#153">153</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#165">165</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#171">171</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#183">183</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#184">184</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#185">185</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#186">186</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#214">214</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#221">221</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#234">234</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#237">237</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#243">243</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#248">248</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#251">251</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#252">252</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#256">256</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#260">260</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#261">261</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#262">262</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#263">263</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#265">265</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#268">268</A> to DR. 
  Changed status of issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#49">49</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#109">109</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#117">117</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#182">182</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#228">228</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#230">230</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#232">232</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#235">235</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#238">238</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#241">241</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#242">242</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#250">250</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#259">259</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#264">264</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#266">266</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#267">267</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#271">271</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#272">272</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#273">273</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#275">275</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#281">281</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#284">284</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#285">285</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#286">286</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#288">288</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#292">292</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#295">295</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#297">297</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#298">298</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#301">301</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#303">303</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#306">306</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#307">307</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#308">308</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#312">312</A> to Ready. 
  Closed issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#111">111</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#277">277</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#279">279</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#287">287</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#289">289</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#293">293</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#302">302</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#313">313</A> <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#314">314</A> as NAD. 
  <LI>R17: Pre-Copenhagen mailing. Converted issues list to XML. Added proposed 
  resolutions for issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#49">49</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#76">76</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#91">91</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#235">235</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#250">250</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#267">267</A>. Added new 
  issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#278">278</A>-<A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#311">311</A>. 
  <LI>R16: post-Toronto mailing; reflects actions taken in Toronto. Added new 
  issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#265">265</A>-<A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#277">277</A>. Changed 
  status of issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#3">3</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#8">8</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#9">9</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#19">19</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#26">26</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#31">31</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#61">61</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#63">63</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#86">86</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#108">108</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#112">112</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#114">114</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#115">115</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#122">122</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#127">127</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#129">129</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#134">134</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#137">137</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#142">142</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#144">144</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#146">146</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#147">147</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#159">159</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#164">164</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#170">170</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#181">181</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#199">199</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#208">208</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#209">209</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#210">210</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#211">211</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#212">212</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#217">217</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#220">220</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#222">222</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#223">223</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#224">224</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#227">227</A> to "DR". 
  Reopened issue <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#23">23</A>. Reopened 
  issue <A href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#187">187</A>. 
  Changed issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#2">2</A> and <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#4">4</A> to NAD. Fixed 
  a typo in issue <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#17">17</A>. Fixed 
  issue <A href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#70">70</A>: 
  signature should be changed both places it appears. Fixed issue <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#160">160</A>: previous 
  version didn't fix the bug in enough places. 
  <LI>R15: pre-Toronto mailing. Added issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#233">233</A>-<A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#264">264</A>. Some 
  small HTML formatting changes so that we pass Weblint tests. 
  <LI>R14: post-Tokyo II mailing; reflects committee actions taken in Tokyo. 
  Added issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#228">228</A> to <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#232">232</A>. 
  (00-0019R1/N1242) 
  <LI>R13: pre-Tokyo II updated: Added issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#212">212</A> to <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#227">227</A>. 
  <LI>R12: pre-Tokyo II mailing: Added issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#199">199</A> to <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#211">211</A>. Added 
  "and paragraph 5" to the proposed resolution of issue <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#29">29</A>. Add 
  further rationale to issue <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#178">178</A>. 
  <LI>R11: post-Kona mailing: Updated to reflect LWG and full committee actions 
  in Kona (99-0048/N1224). Note changed resolution of issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#4">4</A> and <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#38">38</A>. Added 
  issues <A href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#196">196</A> 
  to <A href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#198">198</A>. 
  Closed issues list split into "defects" and "closed" documents. Changed the 
  proposed resolution of issue <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#4">4</A> to NAD, and 
  changed the wording of proposed resolution of issue <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#38">38</A>. 
  <LI>R10: pre-Kona updated. Added proposed resolutions <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#83">83</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#86">86</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#91">91</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#92">92</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#109">109</A>. Added 
  issues <A href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#190">190</A> 
  to <A href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#195">195</A>. 
  (99-0033/D1209, 14 Oct 99) 
  <LI>R9: pre-Kona mailing. Added issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#140">140</A> to <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#189">189</A>. Issues 
  list split into separate "active" and "closed" documents. (99-0030/N1206, 25 
  Aug 99) 
  <LI>R8: post-Dublin mailing. Updated to reflect LWG and full committee actions 
  in Dublin. (99-0016/N1193, 21 Apr 99) 
  <LI>R7: pre-Dublin updated: Added issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#130">130</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#131">131</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#132">132</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#133">133</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#134">134</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#135">135</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#136">136</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#137">137</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#138">138</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#139">139</A> (31 Mar 
  99) 
  <LI>R6: pre-Dublin mailing. Added issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#127">127</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#128">128</A>, and <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#129">129</A>. 
  (99-0007/N1194, 22 Feb 99) 
  <LI>R5: update issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#103">103</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#112">112</A>; added 
  issues <A href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#114">114</A> 
  to <A href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#126">126</A>. 
  Format revisions to prepare for making list public. (30 Dec 98) 
  <LI>R4: post-Santa Cruz II updated: Issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#110">110</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#111">111</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#112">112</A>, <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#113">113</A> added, 
  several issues corrected. (22 Oct 98) 
  <LI>R3: post-Santa Cruz II: Issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#94">94</A> to <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#109">109</A> added, 
  many issues updated to reflect LWG consensus (12 Oct 98) 
  <LI>R2: pre-Santa Cruz II: Issues <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#73">73</A> to <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#93">93</A> added, issue 
  <A href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#17">17</A> updated. 
  (29 Sep 98) 
  <LI>R1: Correction to issue <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#55">55</A> resolution, 
  <A href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#60">60</A> code 
  format, <A href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#64">64</A> 
  title. (17 Sep 98) </LI></UL>
<H2><A name=Status></A>Issue Status</H2>
<P><B><A name=New>New</A></B> - The issue has not yet been reviewed by the LWG. 
Any <B>Proposed Resolution</B> is purely a suggestion from the issue submitter, 
and should not be construed as the view of LWG.</P>
<P><B><A name=Open>Open</A></B> - The LWG has discussed the issue but is not yet 
ready to move the issue forward. There are several possible reasons for open 
status:</P>
<UL>
  <LI>Consensus may have not yet have been reached as to how to deal with the 
  issue. 
  <LI>Informal consensus may have been reached, but the LWG awaits exact 
  <B>Proposed Resolution</B> wording for review. 
  <LI>The LWG wishes to consult additional technical experts before proceeding. 
  <LI>The issue may require further study. </LI></UL>
<P>A <B>Proposed Resolution</B> for an open issue is still not be construed as 
the view of LWG. Comments on the current state of discussions are often given at 
the end of open issues in an italic font. Such comments are for information only 
and should not be given undue importance.</P>
<P><B><A name=Dup>Dup</A></B> - The LWG has reached consensus that the issue is 
a duplicate of another issue, and will not be further dealt with. A 
<B>Rationale</B> identifies the duplicated issue's issue number. </P>
<P><B><A name=NAD>NAD</A></B> - The LWG has reached consensus that the issue is 
not a defect in the Standard, and the issue is ready to forward to the full 
committee as a proposed record of response. A <B>Rationale</B> discusses the 
LWG's reasoning.</P>
<P><B><A name=Review>Review</A></B> - Exact wording of a <B>Proposed 
Resolution</B> is now available for review on an issue for which the LWG 
previously reached informal consensus.</P>
<P><B><A name=Ready>Ready</A></B> - The LWG has reached consensus that the issue 
is a defect in the Standard, the <B>Proposed Resolution</B> is correct, and the 
issue is ready to forward to the full committee for further action as a Defect 
Report (DR).</P>
<P><B><A name=DR>DR</A></B> - (Defect Report) - The full J16 committee has voted 
to forward the issue to the Project Editor to be processed as a Potential Defect 
Report. The Project Editor reviews the issue, and then forwards it to the WG21 
Convenor, who returns it to the full committee for final disposition. This 
issues list accords the status of DR to all these Defect Reports regardless of 
where they are in that process.</P>
<P><B><A name=TC>TC</A></B> - (Technical Corrigenda) - The full WG21 committee 
has voted to accept the Defect Report's Proposed Resolution as a Technical 
Corrigenda. Action on this issue is thus complete and no further action is 
possible under ISO rules.</P>
<P><B><A name=RR>RR</A></B> - (Record of Response) - The full WG21 committee has 
determined that this issue is not a defect in the Standard. Action on this issue 
is thus complete and no further action is possible under ISO rules.</P>
<P><B><A name=Future>Future</A></B> - In addition to the regular status, the LWG 
believes that this issue should be revisited at the next revision of the 
standard. It is usually paired with NAD.</P>
<P>Issues are always given the status of <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#New">New</A> when they 
first appear on the issues list. They may progress to <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A> or <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Review">Review</A> while 
the LWG is actively working on them. When the LWG has reached consensus on the 
disposition of an issue, the status will then change to <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Dup">Dup</A>, <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#NAD">NAD</A>, or <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A> as 
appropriate. Once the full J16 committee votes to forward Ready issues to the 
Project Editor, they are given the status of Defect Report ( <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#DR">DR</A>). These in 
turn may become the basis for Technical Corrigenda (<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#TC">TC</A>), or are 
closed without action other than a Record of Response (<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#RR">RR</A> ). The intent 
of this LWG process is that only issues which are truly defects in the Standard 
move to the formal ISO DR status. </P>
<H2>Active Issues</H2>
<HR>
<A name=23>
<H3>23.&nbsp;Num_get overflow result</H3></A>
<P><B>Section:</B>&nbsp;22.2.2.1.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.facet.num.get.virtuals">[lib.facet.num.get.virtuals]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Nathan Myers&nbsp; <B>Date:</B>&nbsp;6 Aug 1998</P>
<P>The current description of numeric input does not account for the possibility 
of overflow. This is an implicit result of changing the description to rely on 
the definition of scanf() (which fails to report overflow), and conflicts with 
the documented behavior of traditional and current implementations. </P>
<P>Users expect, when reading a character sequence that results in a value 
unrepresentable in the specified type, to have an error reported. The standard 
as written does not permit this. </P>
<P><B>Further comments from Dietmar:</B></P>
<P>I don't feel comfortable with the proposed resolution to issue 23: It kind of 
simplifies the issue to much. Here is what is going on: </P>
<P>Currently, the behavior of numeric overflow is rather counter intuitive and 
hard to trace, so I will describe it briefly: </P>
<UL>
  <LI>According to 22.2.2.1.2 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.facet.num.get.virtuals">[lib.facet.num.get.virtuals]</A> 
  paragraph 11 <TT>failbit</TT> is set if <TT>scanf()</TT> would return an input 
  error; otherwise a value is converted to the rules of <TT>scanf</TT>. 
  <LI><TT>scanf()</TT> is defined in terms of <TT>fscanf()</TT>. 
  <LI><TT>fscanf()</TT> returns an input failure if during conversion no 
  character matching the conversion specification could be extracted before 
  reaching EOF. This is the only reason for <TT>fscanf()</TT> to fail due to an 
  input error and clearly does not apply to the case of overflow. 
  <LI>Thus, the conversion is performed according to the rules of 
  <TT>fscanf()</TT> which basically says that <TT>strtod</TT>, 
  <TT>strtol()</TT>, etc. are to be used for the conversion. 
  <LI>The <TT>strtod()</TT>, <TT>strtol()</TT>, etc. functions consume as many 
  matching characters as there are and on overflow continue to consume matching 
  characters but also return a value identical to the maximum (or minimum for 
  signed types if there was a leading minus) value of the corresponding type and 
  set <TT>errno</TT> to <TT>ERANGE</TT>. 
  <LI>Thus, according to the current wording in the standard, overflows can be 
  detected! All what is to be done is to check <TT>errno</TT> after reading an 
  element and, of course, clearing <TT>errno</TT> before trying a conversion. 
  With the current wording, it can be detected whether the overflow was due to a 
  positive or negative number for signed types. </LI></UL>
<P><B>Further discussion from Redmond:</B></P>
<P>The basic problem is that we've defined our behavior, including our 
error-reporting behavior, in terms of C90. However, C90's method of reporting 
overflow in scanf is not technically an "input error". The <TT>strto_*</TT> 
functions are more precise.</P>
<P>There was general consensus that <TT>failbit</TT> should be set upon 
overflow. We considered three options based on this:</P>
<OL>
  <LI>Set failbit upon conversion error (including overflow), and don't store 
  any value. 
  <LI>Set failbit upon conversion error, and also set <TT>errno</TT> to 
  indicated the precise nature of the error. 
  <LI>Set failbit upon conversion error. If the error was due to overflow, store 
  +-numeric_limits&lt;T&gt;::max() as an overflow indication. </LI></OL>
<P>Straw poll: (1) 5; (2) 0; (3) 8.</P>
<P><B>Further discussion from Santa Cruz:</B></P>
<P>There was some discussion of what the intent of our error reporting mechanism 
was. There was general agreement on the following principles:</P>
<UL>
  <LI>We want to convert strings to numbers in the same way as the C 
  <TT>strto*</TT> functions do. The same things that those functions would 
  consider errors, we consider errors. 
  <LI>Overflow is an error. Floating-point underflow is not an error. 
  1.e-9999999, for example, should be treated as 0. (A negative number whose 
  magnitude is too large is still overflow, and is just the same error as a 
  positive number whose magnitude is too large. Finally, <TT>strtoul</TT> 
  already specifies what happens if you try to convert a sequence beginning with 
  a minus sign into an unsigned value.) 
  <LI>Our mechanism for reporting errors is to set failbit. Our mechanism is not 
  errno. Nothing in the standard should require or imply that streams or facets 
  ever set errno. (Even if some implementations might have that effect.) 
</LI></UL>
<P>The crux of the disagreement was that some people, but not all, believed that 
the design was also based on a fourth principle: whenever converstion fails and 
failbit is set, nothing is to be extracted and the value of the variable being 
extracted into is guaranteed to be unchanged.</P>
<P>Some people believe that upon overflow, an implementation should "extract" a 
special value that allows the user to tell that it was overflow instead of some 
other kind of error. Straw poll: 1 person believed the standard should require 
that, 2 thought it should forbid it, and 6 thought the standard should allow but 
not require it.</P>
<P>PJP will provide wording.</P>
<P><B>Proposed resolution:</B></P>
<HR>
<A name=44>
<H3>44.&nbsp;Iostreams use operator== on int_type values</H3></A>
<P><B>Section:</B>&nbsp;27 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.input.output">[lib.input.output]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Nathan Myers&nbsp; <B>Date:</B>&nbsp;6 Aug 1998</P>
<P>Many of the specifications for iostreams specify that character values or 
their int_type equivalents are compared using operators == or !=, though in 
other places traits::eq() or traits::eq_int_type is specified to be used 
throughout. This is an inconsistency; we should change uses of == and != to use 
the traits members instead. </P>
<P><B>Proposed resolution:</B></P>
<P><I>[Kona: Nathan to supply proposed wording]</I></P>
<P><I>[ Tokyo: the LWG reaffirmed that this is a defect, and requires careful 
review of clause 27 as the changes are context sensitive. ]</I></P>
<HR>
<A name=92>
<H3>92.&nbsp;Incomplete Algorithm Requirements</H3></A>
<P><B>Section:</B>&nbsp;25 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-algorithms.html#lib.algorithms">[lib.algorithms]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Nico Josuttis&nbsp; <B>Date:</B>&nbsp;29 Sep 1998</P>
<P>The standard does not state, how often a function object is copied, called, 
or the order of calls inside an algorithm. This may lead to surprising/buggy 
behavior. Consider the following example: </P><PRE>class Nth {    // function object that returns true for the nth element 
  private: 
    int nth;     // element to return true for 
    int count;   // element counter 
  public: 
    Nth (int n) : nth(n), count(0) { 
    } 
    bool operator() (int) { 
        return ++count == nth; 
    } 
}; 
.... 
// remove third element 
    list&lt;int&gt;::iterator pos; 
    pos = remove_if(coll.begin(),coll.end(),  // range 
                    Nth(3)),                  // remove criterion 
    coll.erase(pos,coll.end()); </PRE>
<P>This call, in fact removes the 3rd <B>AND the 6th</B> element. This happens 
because the usual implementation of the algorithm copies the function object 
internally: </P><PRE>template &lt;class ForwIter, class Predicate&gt; 
ForwIter std::remove_if(ForwIter beg, ForwIter end, Predicate op) 
{ 
    beg = find_if(beg, end, op); 
    if (beg == end) { 
        return beg; 
    } 
    else { 
        ForwIter next = beg; 
        return remove_copy_if(++next, end, beg, op); 
    } 
} </PRE>
<P>The algorithm uses find_if() to find the first element that should be 
removed. However, it then uses a copy of the passed function object to process 
the resulting elements (if any). Here, Nth is used again and removes also the 
sixth element. This behavior compromises the advantage of function objects being 
able to have a state. Without any cost it could be avoided (just implement it 
directly instead of calling find_if()). </P>
<P><B>Proposed resolution:</B></P>
<P><I>[Dublin: Pete Becker felt that this may not be a defect, but rather 
something that programmers need to be educated about. There was discussion of 
adding wording to the effect that the number and order of calls to function 
objects, including predicates, not affect the behavior of the function 
object.]</I></P>
<P><I>[Pre-Kona: Nico comments: It seems the problem is that we don't have a 
clear statement of "predicate" in the standard. People including me seemed to 
think "a function returning a Boolean value and being able to be called by an 
STL algorithm or be used as sorting criterion or ... is a predicate". But a 
predicate has more requirements: It should never change its behavior due to a 
call or being copied. IMHO we have to state this in the standard. If you like, 
see section 8.1.4 of my library book for a detailed discussion.]</I></P>
<P><I>[Kona: Nico will provide wording to the effect that "unless otherwise 
specified, the number of copies of and calls to function objects by algorithms 
is unspecified".&nbsp; Consider placing in 25 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-algorithms.html#lib.algorithms">[lib.algorithms]</A> 
after paragraph 9.]</I></P>
<P><I>[Santa Cruz: The standard doesn't currently guarantee that functions 
object won't be copied, and what isn't forbidden is allowed. It is believed 
(especially since implementations that were written in concert with the standard 
do make copies of function objects) that this was intentional. Thus, no 
normative change is needed. What we should put in is a non-normative note 
suggesting to programmers that if they want to guarantee the lack of copying 
they should use something like the <TT>ref</TT> wrapper. Dave will provide 
wording for that note.]</I></P>
<HR>
<A name=96>
<H3>96.&nbsp;Vector&lt;bool&gt; is not a container</H3></A>
<P><B>Section:</B>&nbsp;23.2.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-containers.html#lib.vector.bool">[lib.vector.bool]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;AFNOR&nbsp; <B>Date:</B>&nbsp;7 Oct 1998</P>
<P><TT>vector&lt;bool&gt;</TT> is not a container as its reference and pointer 
types are not references and pointers. </P>
<P>Also it forces everyone to have a space optimization instead of a speed 
one.</P>
<P><B>See also:</B> 99-0008 == N1185 Vector&lt;bool&gt; is Nonconforming, Forces 
Optimization Choice.</P>
<P><B>Proposed resolution:</B></P>
<P><I>[In Santa Cruz the LWG felt that this was Not A Defect.]</I></P>
<P><I>[In Dublin many present felt that failure to meet Container requirements 
was a defect. There was disagreement as to whether or not the optimization 
requirements constituted a defect.]</I></P>
<P><I>[The LWG looked at the following resolutions in some detail: 
<BR>&nbsp;&nbsp;&nbsp;&nbsp; * Not A Defect.<BR>&nbsp;&nbsp;&nbsp;&nbsp; * Add a 
note explaining that vector&lt;bool&gt; does not meet Container 
requirements.<BR>&nbsp;&nbsp;&nbsp;&nbsp; * Remove 
vector&lt;bool&gt;.<BR>&nbsp;&nbsp;&nbsp;&nbsp; * Add a new category of 
container requirements which vector&lt;bool&gt; would 
meet.<BR>&nbsp;&nbsp;&nbsp;&nbsp; * Rename vector&lt;bool&gt;.<BR><BR>No 
alternative had strong, wide-spread, support and every alternative had at least 
one "over my dead body" response.<BR><BR>There was also mention of a transition 
scheme something like (1) add vector_bool and deprecate vector&lt;bool&gt; in 
the next standard. (2) Remove vector&lt;bool&gt; in the following 
standard.]</I></P>
<P><I>[Modifying container requirements to permit returning proxies (thus 
allowing container requirements conforming vector&lt;bool&gt;) was also 
discussed.]</I></P>
<P><I>[It was also noted that there is a partial but ugly workaround in that 
vector&lt;bool&gt; may be further specialized with a customer 
allocator.]</I></P>
<P><I>[Kona: Herb Sutter presented his paper J16/99-0035==WG21/N1211, 
vector&lt;bool&gt;: More Problems, Better Solutions. Much discussion of a two 
step approach: a) deprecate, b) provide replacement under a new name. LWG straw 
vote on that: 1-favor, 11-could live with, 2-over my dead body. This resolution 
was mentioned in the LWG report to the full committee, where several additional 
committee members indicated over-my-dead-body positions.]</I></P>
<P><I>[Tokyo: Not discussed by the full LWG; no one claimed new insights and so 
time was more productively spent on other issues. In private discussions it was 
asserted that requirements for any solution include 1) Increasing the full 
committee's understanding of the problem, and 2) providing compiler vendors, 
authors, teachers, and of course users with specific suggestions as to how to 
apply the eventual solution.]</I></P>
<HR>
<A name=98>
<H3>98.&nbsp;Input iterator requirements are badly written</H3></A>
<P><B>Section:</B>&nbsp;24.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.input.iterators">[lib.input.iterators]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Review">Review</A>&nbsp; 
<B>Submitter:</B>&nbsp;AFNOR&nbsp; <B>Date:</B>&nbsp;7 Oct 1998</P>
<P>Table 72 in 24.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.input.iterators">[lib.input.iterators]</A> 
specifies semantics for <TT>*r++</TT> of:</P>
<P>&nbsp;&nbsp; <TT>{ T tmp = *r; ++r; return tmp; }</TT> </P>
<P>There are two problems with this. First, the return type is specified to be 
"T", as opposed to something like "convertible to T". This is too specific: we 
want to allow *r++ to return an lvalue.</P>
<P>Second, writing the semantics in terms of code misleadingly suggests that the 
effects *r++ should precisely replicate the behavior of this code, including 
side effects. (Does this mean that *r++ should invoke the copy constructor 
exactly as many times as the sample code above would?) See issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#334">334</A> for a 
similar problem.</P>
<P><B>Proposed resolution:</B></P>In Table 72 in 24.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.input.iterators">[lib.input.iterators]</A>, 
change the return type for <TT>*r++</TT> from <TT>T</TT> to "convertible to T". 
<P><B>Rationale:</B></P>
<P>This issue has two parts: the return type, and the number of times the copy 
constructor is invoked.</P>
<P>The LWG believes the the first part is a real issue. It's inappropriate for 
the return type to be specified so much more precisely for *r++ than it is for 
*r. In particular, if r is of (say) type <TT>int*</TT>, then *r++ isn't 
<TT>int</TT>, but <TT>int&amp;</TT>.</P>
<P>The LWG does not believe that the number of times the copy constructor is 
invoked is a real issue. This can vary in any case, because of language rules on 
copy constructor elision. That's too much to read into these semantics 
clauses.</P>
<HR>
<A name=120>
<H3>120.&nbsp;Can an implementor add specializations?</H3></A>
<P><B>Section:</B>&nbsp;17.4.3.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.reserved.names">[lib.reserved.names]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Review">Review</A>&nbsp; 
<B>Submitter:</B>&nbsp;Judy Ward&nbsp; <B>Date:</B>&nbsp;15 Dec 1998</P>
<P>The original issue asked whether a library implementor could specialize 
standard library templates for built-in types. (This was an issue because users 
are permitted to explicitly instantiate standard library templates.)</P>
<P>Specializations are no longer a problem, because of the resolution to core 
issue 259. Under the proposed resolution, it will be legal for a translation 
unit to contain both a specialization and an explicit instantiation of the same 
template, provided that the specialization comes first. In such a case, the 
explicit instantiation will be ignored. Further discussion of library issue 120 
assumes that the core 259 resolution will be adopted.</P>
<P>However, as noted in lib-7047, one piece of this issue still remains: what 
happens if a standard library implementor explicitly instantiates a standard 
library templates? It's illegal for a program to contain two different explicit 
instantiations of the same template for the same type in two different 
translation units (ODR violation), and the core working group doesn't believe it 
is practical to relax that restriction.</P>
<P>The issue, then, is: are users allowed to explicitly instantiate standard 
library templates for non-user defined types? The status quo answer is 'yes'. 
Changing it to 'no' would give library implementors more freedom.</P>
<P>This is an issue because, for performance reasons, library implementors often 
need to explicitly instantiate standard library templates. (for example, 
std::basic_string&lt;char&gt;) Does giving users freedom to explicitly 
instantiate standard library templates for non-user defined types make it 
impossible or painfully difficult for library implementors to do this?</P>
<P>John Spicer suggests, in lib-8957, that library implementors have a mechanism 
they can use for explicit instantiations that doesn't prevent users from 
performing their own explicit instantiations: put each explicit instantiation in 
its own object file. (Different solutions might be necessary for Unix DSOs or 
MS-Windows DLLs.) On some platforms, library implementors might not need to do 
anything special: the "undefined behavior" that results from having two 
different explicit instantiations might be harmless.</P>
<P><B>Proposed resolution:</B></P>
<P>Append to 17.4.3.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.reserved.names">[lib.reserved.names]</A> 
paragraph 1: </P>
<BLOCKQUOTE>A program may explicitly instantiate any templates in the standard 
  library only if the declaration depends on a user-defined name of external 
  linkage and the instantiation meets the standard library requirements for the 
  original template. </BLOCKQUOTE>
<P><B>Rationale:</B></P>
<P>The LWG considered another possible resolution:</P>
<BLOCKQUOTE>
  <P>In light of the resolution to core issue 259, no normative changes in the 
  library clauses are necessary. Add the following non-normative note to the end 
  of 17.4.3.1 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.reserved.names">[lib.reserved.names]</A> 
  paragraph 1:</P>
  <BLOCKQUOTE>[<I>Note:</I> A program may explicitly instantiate standard 
    library templates, even when an explicit instantiation does not depend on a 
    user-defined name. <I>--end note</I>] </BLOCKQUOTE></BLOCKQUOTE>
<P>The LWG rejected this because it was believed that it would make it 
unnecessarily difficult for library implementors to write high-quality 
implementations. A program may not include an explicit instantiation of the same 
template, for the same template arguments, in two different translation units. 
If users are allowed to provide explicit instantiations of Standard Library 
templates for built-in types, then library implementors aren't, at least not 
without nonportable tricks.</P>
<P>The most serious problem is a class template that has writeable static member 
variables. Unfortunately, such class templates are important and, in existing 
Standard Library implementations, are often explicitly specialized by library 
implementors: locale facets, which have a writeable static member variable 
<TT>id</TT>. If a user's explicit instantiation collided with the 
implementations explicit instantiation, iostream initialization could cause 
locales to be constructed in an inconsistent state.</P>
<P>One proposed implementation technique was for Standard Library implementors 
to provide explicit instantiations in separate object files, so that they would 
not be picked up by the linker when the user also provides an explicit 
instantiation. However, this technique only applies for Standard Library 
implementations that are packaged as static archives. Most Standard Library 
implementations nowadays are packaged as dynamic libraries, so this technique 
would not apply.</P>
<P>The Committee is now considering standardization of dynamic linking. If there 
are such changes in the future, it may be appropriate to revisit this issue 
later.</P>
<HR>
<A name=167>
<H3>167.&nbsp;Improper use of <TT>traits_type::length()</TT> </H3></A>
<P><B>Section:</B>&nbsp;27.6.2.5.4 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.ostream.inserters.character">[lib.ostream.inserters.character]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Review">Review</A>&nbsp; 
<B>Submitter:</B>&nbsp;Dietmar Khl&nbsp; <B>Date:</B>&nbsp;20 Jul 1999</P>
<P>Paragraph 4 states that the length is determined using 
<TT>traits::length(s)</TT>. Unfortunately, this function is not defined for 
example if the character type is <TT>wchar_t</TT> and the type of <TT>s</TT> is 
<TT>char const*</TT>. Similar problems exist if the character type is 
<TT>char</TT> and the type of <TT>s</TT> is either <TT>signed char const*</TT> 
or <TT>unsigned char const*</TT>.</P>
<P><B>Proposed resolution:</B></P>
<P>Change 27.6.2.5.4 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.ostream.inserters.character">[lib.ostream.inserters.character]</A> 
paragraph 4 from:</P>
<BLOCKQUOTE>
  <P>Effects: Behaves like an formatted inserter (as described in 
  lib.ostream.formatted.reqmts) of out. After a sentry object is constructed it 
  inserts characters. The number of characters starting at s to be inserted is 
  traits::length(s). Padding is determined as described in 
  lib.facet.num.put.virtuals. The traits::length(s) characters starting at s are 
  widened using out.widen (lib.basic.ios.members). The widened characters and 
  any required padding are inserted into out. Calls width(0).</P></BLOCKQUOTE>
<P>to:</P>
<BLOCKQUOTE>
  <P>Effects: Behaves like an formatted inserter (as described in 
  lib.ostream.formatted.reqmts) of out. After a sentry object is constructed it 
  inserts <I>n</I> characters starting at <I>s</I>, where <I>n</I> is:</P>
  <UL>
    <LI>traits::length(s) for the overload where the first argument is of type 
    basic_ostream&lt;charT, traits&gt;&amp; and the second is of type const 
    charT*, and also for the overload where the first argument is of type 
    basic_ostream&lt;char, traits&gt;&amp; and the second is of type const 
    char*. 
    <LI>std::char_traits&lt;char&gt;::length(s) for the overload where the first 
    argument is of type basic_ostream&lt;charT, traits&gt;&amp; and the second 
    is of type const char*. 
    <LI>traits::length(reinterpret_cast&lt;const char*&gt;(s)) for the other two 
    overloads. </LI></UL>
  <P>Padding is determined as described in lib.facet.num.put.virtuals. The 
  <I>n</I> characters starting at <I>s</I> are widened using out.widen 
  (lib.basic.ios.members). The widened characters and any required padding are 
  inserted into out. Calls width(0).</P></BLOCKQUOTE>
<P><I>[Santa Cruz: Matt supplied new wording]</I></P>
<P><B>Rationale:</B></P>
<P>We have five separate cases. In two of them we can use the user-supplied 
traits class without any fuss. In the other three we try to use something as 
close to that user-supplied class as possible. In two cases we've got a traits 
class that's appropriate for char and what we've got is a const signed char* or 
a const unsigned char*; that's close enough so we can just use a reinterpret 
cast, and continue to use the user-supplied traits class. Finally, there's one 
case where we just have to give up: where we've got a traits class for some 
arbitrary charT type, and we somehow have to deal with a const char*. There's 
nothing better to do but fall back to char_traits&lt;char&gt;</P>
<HR>
<A name=187>
<H3>187.&nbsp;iter_swap underspecified</H3></A>
<P><B>Section:</B>&nbsp;25.2.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-algorithms.html#lib.alg.swap">[lib.alg.swap]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A>&nbsp; 
<B>Submitter:</B>&nbsp;Andrew Koenig&nbsp; <B>Date:</B>&nbsp;14 Aug 1999</P>
<P>The description of iter_swap in 25.2.2 paragraph 7,says that it ``exchanges 
the values'' of the objects to which two iterators refer.<BR><BR>What it doesn't 
say is whether it does so using swap or using the assignment operator and copy 
constructor.<BR><BR>This question is an important one to answer, because swap is 
specialized to work efficiently for standard containers.<BR>For example:</P>
<BLOCKQUOTE><PRE>vector&lt;int&gt; v1, v2;
iter_swap(&amp;v1, &amp;v2);</PRE></BLOCKQUOTE>
<P>Is this call to iter_swap equivalent to calling swap(v1, v2)?&nbsp; Or is it 
equivalent to</P>
<BLOCKQUOTE><PRE>{
vector&lt;int&gt; temp = v1;
v1 = v2;
v2 = temp;
}</PRE></BLOCKQUOTE>
<P>The first alternative is O(1); the second is O(n).</P>
<P>A LWG member, Dave Abrahams, comments:</P>
<BLOCKQUOTE>
  <P>Not an objection necessarily, but I want to point out the cost of that 
  requirement:</P>
  <BLOCKQUOTE>
    <P><TT>iter_swap(list&lt;T&gt;::iterator, 
  list&lt;T&gt;::iterator)</TT></P></BLOCKQUOTE>
  <P>can currently be specialized to be more efficient than iter_swap(T*,T*) for 
  many T (by using splicing). Your proposal would make that optimization 
  illegal.&nbsp;</P></BLOCKQUOTE>
<P><I>[Kona: The LWG notes the original need for iter_swap was proxy iterators 
which are no longer permitted.]</I></P>
<P><B>Proposed resolution:</B></P>
<P>Change the effect clause of iter_swap in 25.2.2 paragraph 7 from:</P>
<BLOCKQUOTE>
  <P>Exchanges the values pointed to by the two iterators a and 
b.</P></BLOCKQUOTE>
<P>to</P>
<BLOCKQUOTE>
  <P><TT>swap(*a, *b)</TT>.</P></BLOCKQUOTE>
<P><B>Rationale:</B></P>
<P>It's useful to say just what <TT>iter_swap</TT> does. There may be some 
iterators for which we want to specialize <TT>iter_swap</TT>, but the fully 
general version should have a general specification.</P>
<P>Note that in the specific case of <TT>list&lt;T&gt;::iterator</TT>, iter_swap 
should not be specialized as suggested above. That would do much more than 
exchanging the two iterators' values: it would change predecessor/successor 
relationships, possibly moving the iterator from one list to another. That would 
surely be inappropriate.</P>
<HR>
<A name=197>
<H3>197.&nbsp;max_size() underspecified</H3></A>
<P><B>Section:</B>&nbsp;20.1.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-utilities.html#lib.allocator.requirements">[lib.allocator.requirements]</A>, 
23.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-containers.html#lib.container.requirements">[lib.container.requirements]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Andy Sawyer&nbsp; <B>Date:</B>&nbsp;21 Oct 1999</P>
<P>Must the value returned by max_size() be unchanged from call to call? </P>
<P>Must the value returned from max_size() be meaningful? </P>
<P>Possible meanings identified in lib-6827: </P>
<P>1) The largest container the implementation can support given "best case" 
conditions - i.e. assume the run-time platform is "configured to the max", and 
no overhead from the program itself. This may possibly be determined at the 
point the library is written, but certainly no later than compile 
time.<BR><BR>2) The largest container the program could create, given "best 
case" conditions - i.e. same platform assumptions as (1), but take into account 
any overhead for executing the program itself. (or, roughly 
"storage=storage-sizeof(program)"). This does NOT include any resource allocated 
by the program. This may (or may not) be determinable at compile time.<BR><BR>3) 
The largest container the current execution of the program could create, given 
knowledge of the actual run-time platform, but again, not taking into account 
any currently allocated resource. This is probably best determined at program 
start-up.<BR><BR>4) The largest container the current execution program could 
create at the point max_size() is called (or more correctly at the point 
max_size() returns :-), given it's current environment (i.e. taking into account 
the actual currently available resources). This, obviously, has to be determined 
dynamically each time max_size() is called. </P>
<P><B>Proposed resolution:</B></P>
<P>Change 20.1.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-utilities.html#lib.allocator.requirements">[lib.allocator.requirements]</A> 
table 32 max_size() wording from:<BR><BR>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; the 
largest value that can meaningfully be passed to 
X::allocate<BR>to:<BR>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; the value of the largest 
constant expression (5.19 <A 
href="file:///P:/j16/33-pre-oxford/lwg/expr.html#expr.const">[expr.const]</A>) 
that could ever meaningfully be passed to X::allocate</P>
<P>Change 23.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-containers.html#lib.container.requirements">[lib.container.requirements]</A> 
table 65 max_size() wording from:<BR><BR>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; size() 
of the largest possible container.<BR>to:<BR>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; the 
value of the largest constant expression (5.19 <A 
href="file:///P:/j16/33-pre-oxford/lwg/expr.html#expr.const">[expr.const]</A>) 
that could ever meaningfully be returned by X::size(). </P>
<P><I>[Kona: The LWG informally discussed this and asked Andy Sawyer to submit 
an issue.]</I></P>
<P><I>[Tokyo: The LWG believes (1) above is the intended meaning.]</I></P>
<P><I>[Post-Tokyo: Beman Dawes supplied the above resolution at the request of 
the LWG. 21.3.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-strings.html#lib.string.capacity">[lib.string.capacity]</A> 
was not changed because it references max_size() in 23.1. The term 
"compile-time" was avoided because it is not defined anywhere in the standard 
(even though it is used several places in the library clauses).]</I></P>
<P><I>[Copenhagen: Exactly what <TT>max_size</TT> means is still unclear. It may 
have a different meaning as a container member function than as an allocator 
member function. For the latter, it is probably best thought of as an 
architectural limit. Nathan will provide new wording.]</I></P>
<HR>
<A name=201>
<H3>201.&nbsp;Numeric limits terminology wrong</H3></A>
<P><B>Section:</B>&nbsp;18.2.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-support.html#lib.limits">[lib.limits]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Stephen Cleary&nbsp; <B>Date:</B>&nbsp;21 Dec 1999</P>
<P>In some places in this section, the terms "fundamental types" and "scalar 
types" are used when the term "arithmetic types" is intended. The current usage 
is incorrect because void is a fundamental type and pointers are scalar types, 
neither of which should have specializations of numeric_limits. </P>
<P><B>Proposed resolution:</B></P>
<P>Change 18.2 [lib.support.limits] para 1 from:</P>
<BLOCKQUOTE>
  <P>The headers &lt;limits&gt;, &lt;climits&gt;, and &lt;cfloat&gt; supply 
  characteristics of implementation-dependent fundamental types 
(3.9.1).</P></BLOCKQUOTE>
<P>to:</P>
<BLOCKQUOTE>
  <P>The headers &lt;limits&gt;, &lt;climits&gt;, and &lt;cfloat&gt; supply 
  characteristics of implementation-dependent arithmetic types 
(3.9.1).</P></BLOCKQUOTE>
<P>Change 18.2.1 [lib.limits] para 1 from:</P>
<BLOCKQUOTE>
  <P>The numeric_limits component provides a C++ program with information about 
  various properties of the implementation's representation of the fundamental 
  types.</P></BLOCKQUOTE>
<P>to:</P>
<BLOCKQUOTE>
  <P>The numeric_limits component provides a C++ program with information about 
  various properties of the implementation's representation of the arithmetic 
  types.</P></BLOCKQUOTE>
<P>Change 18.2.1 [lib.limits] para 2 from:</P>
<BLOCKQUOTE>
  <P>Specializations shall be provided for each fundamental type. . 
.</P></BLOCKQUOTE>
<P>to:</P>
<BLOCKQUOTE>
  <P>Specializations shall be provided for each arithmetic type. . 
.</P></BLOCKQUOTE>
<P>Change 18.2.1 [lib.limits] para 4 from:</P>
<BLOCKQUOTE>
  <P>Non-fundamental standard types. . .</P></BLOCKQUOTE>
<P>to:</P>
<BLOCKQUOTE>
  <P>Non-arithmetic standard types. . .</P></BLOCKQUOTE>
<P>Change 18.2.1.1 [lib.numeric.limits] para 1 from:</P>
<BLOCKQUOTE>
  <P>The member is_specialized makes it possible to distinguish between 
  fundamental types, which have specializations, and non-scalar types, which do 
  not.</P></BLOCKQUOTE>
<P>to:</P>
<BLOCKQUOTE>
  <P>The member is_specialized makes it possible to distinguish between 
  arithmetic types, which have specializations, and non-arithmetic types, which 
  do not.</P></BLOCKQUOTE>
<P><I>[post-Toronto: The opinion of the LWG is that the wording in the standard, 
as well as the wording of the proposed resolution, is flawed. The term 
"arithmetic types" is well defined in C and C++, and it is not clear that the 
term is being used correctly. It is also not clear that the term "implementation 
dependent" has any useful meaning in this context. The biggest problem is that 
numeric_limits seems to be intended both for built-in types and for user-defined 
types, and the standard doesn't make it clear how numeric_limits applies to each 
of those cases. A wholesale review of numeric_limits is needed. A paper would be 
welcome.]</I></P>
<HR>
<A name=225>
<H3>225.&nbsp;std:: algorithms use of other unqualified algorithms</H3></A>
<P><B>Section:</B>&nbsp;17.4.4.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.global.functions">[lib.global.functions]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A>&nbsp; 
<B>Submitter:</B>&nbsp;Dave Abrahams&nbsp; <B>Date:</B>&nbsp;01 Apr 2000</P>
<P>Are algorithms in std:: allowed to use other algorithms without 
qualification, so functions in user namespaces might be found through Koenig 
lookup?</P>
<P>For example, a popular standard library implementation includes this 
implementation of std::unique:</P>
<BLOCKQUOTE><PRE>namespace std {
    template &lt;class _ForwardIter&gt;
    _ForwardIter unique(_ForwardIter __first, _ForwardIter __last) {
      __first = adjacent_find(__first, __last);
      return unique_copy(__first, __last, __first);
    }
    }</PRE></BLOCKQUOTE>
<P>Imagine two users on opposite sides of town, each using unique on his own 
sequences bounded by my_iterators . User1 looks at his standard library 
implementation and says, "I know how to implement a more efficient unique_copy 
for my_iterators", and writes:</P>
<BLOCKQUOTE><PRE>namespace user1 {
    class my_iterator;
    // faster version for my_iterator
    my_iterator unique_copy(my_iterator, my_iterator, my_iterator);
    }</PRE></BLOCKQUOTE>
<P>user1::unique_copy() is selected by Koenig lookup, as he intended.</P>
<P>User2 has other needs, and writes:</P>
<BLOCKQUOTE><PRE>namespace user2 {
    class my_iterator;
    // Returns true iff *c is a unique copy of *a and *b.
    bool unique_copy(my_iterator a, my_iterator b, my_iterator c);
    }</PRE></BLOCKQUOTE>
<P>User2 is shocked to find later that his fully-qualified use of 
std::unique(user2::my_iterator, user2::my_iterator, user2::my_iterator) fails to 
compile (if he's lucky). Looking in the standard, he sees the following Effects 
clause for unique():</P>
<BLOCKQUOTE>
  <P>Effects: Eliminates all but the first element from every consecutive group 
  of equal elements referred to by the iterator i in the range [first, last) for 
  which the following corresponding conditions hold: *i == *(i - 1) or pred(*i, 
  *(i - 1)) != false</P></BLOCKQUOTE>
<P>The standard gives user2 absolutely no reason to think he can interfere with 
std::unique by defining names in namespace user2. His standard library has been 
built with the template export feature, so he is unable to inspect the 
implementation. User1 eventually compiles his code with another compiler, and 
his version of unique_copy silently stops being called. Eventually, he realizes 
that he was depending on an implementation detail of his library and had no 
right to expect his unique_copy() to be called portably.</P>
<P>On the face of it, and given above scenario, it may seem obvious that the 
implementation of unique() shown is non-conforming because it uses unique_copy() 
rather than ::std::unique_copy(). Most standard library implementations, 
however, seem to disagree with this notion.</P>
<P><I>[Tokyo:&nbsp; Steve Adamczyk from the core working group indicates that 
"std::" is sufficient;&nbsp; leading "::" qualification is not required because 
any namespace qualification is sufficient to suppress Koenig lookup.]</I> </P>
<P><B>Proposed resolution:</B></P>
<P>Add a paragraph and a note at the end of 17.4.4.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.global.functions">[lib.global.functions]</A>:</P>
<BLOCKQUOTE>
  <P>Unless otherwise specified, no global or non-member function in the 
  standard library shall use a function from another namespace which is found 
  through <I>argument-dependent name lookup</I> (3.4.2 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/basic.html#basic.lookup.koenig">[basic.lookup.koenig]</A>).</P>
  <P>[Note: the phrase "unless otherwise specified" is intended to allow Koenig 
  lookup in cases like that of ostream_iterators:<BR><BR>Effects:</P>
  <BLOCKQUOTE>
    <P>*out_stream &lt;&lt; value;<BR>if(delim != 0) *out_stream &lt;&lt; 
    delim;<BR>return (*this);</P>
    <P>--end note]</P></BLOCKQUOTE></BLOCKQUOTE>
<P><I>[Tokyo: The LWG agrees that this is a defect in the standard, but is as 
yet unsure if the proposed resolution is the best solution. Furthermore, the LWG 
believes that the same problem of unqualified library names applies to wording 
in the standard itself, and has opened issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#229">229</A> accordingly. 
Any resolution of issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#225">225</A> should be 
coordinated with the resolution of issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#229">229</A>.]</I></P>
<P><I>[Toronto: The LWG is not sure if this is a defect in the standard. Most 
LWG members believe that an implementation of <TT>std::unique</TT> like the one 
quoted in this issue is already illegal, since, under certain circumstances, its 
semantics are not those specified in the standard. The standard's description of 
<TT>unique</TT> does not say that overloading <TT>adjacent_find</TT> should have 
any effect.]</I></P>
<P><I>[Curaao: An LWG-subgroup spent an afternoon working on issues 225, 226, 
and 229. Their conclusion was that the issues should be separated into an LWG 
portion (Howard's paper, N1387=02-0045), and a EWG portion (Dave will write a 
proposal). The LWG and EWG had (separate) discussions of this plan the next day. 
The proposed resolution for this issue is in accordance with Howard's 
paper.]</I></P>
<P><B>Rationale:</B></P>
<P>It could be argued that this proposed isn't strictly necessary, that the 
Standard doesn't grant implementors license to write a standard function that 
behaves differently than specified in the Standard just because of an unrelated 
user-defined name in some other namespace. However, this is at worst a 
clarification. It is surely right that algorithsm shouldn't pick up random 
names, that user-defined names should have no effect unless otherwise specified. 
Issue <A href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#226">226</A> 
deals with the question of when it is appropriate for the standard to explicitly 
specify otherwise.</P>
<HR>
<A name=226>
<H3>226.&nbsp;User supplied specializations or overloads of namespace std 
function templates</H3></A>
<P><B>Section:</B>&nbsp;17.4.3.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.reserved.names">[lib.reserved.names]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Dave Abrahams&nbsp; <B>Date:</B>&nbsp;01 Apr 2000</P>
<P>The issues are:&nbsp;</P>
<P>1. How can a 3rd party library implementor (lib1) write a version of a 
standard algorithm which is specialized to work with his own class 
template?&nbsp;</P>
<P>2. How can another library implementor (lib2) write a generic algorithm which 
will take advantage of the specialized algorithm in lib1?</P>
<P>This appears to be the only viable answer under current language rules:</P>
<BLOCKQUOTE><PRE>namespace lib1
{
    // arbitrary-precision numbers using T as a basic unit
    template &lt;class T&gt;
    class big_num { //...
    };
    </PRE><PRE>    // defining this in namespace std is illegal (it would be an
    // overload), so we hope users will rely on Koenig lookup
    template &lt;class T&gt;
    void swap(big_int&lt;T&gt;&amp;, big_int&lt;T&gt;&amp;);
}</PRE><PRE>#include &lt;algorithm&gt;
namespace lib2
{
    template &lt;class T&gt;
    void generic_sort(T* start, T* end)
    {
            ...
        // using-declaration required so we can work on built-in types
        using std::swap;
        // use Koenig lookup to find specialized algorithm if available
        swap(*x, *y);
    }
}</PRE></BLOCKQUOTE>
<P>This answer has some drawbacks. First of all, it makes writing lib2 difficult 
and somewhat slippery. The implementor needs to remember to write the 
using-declaration, or generic_sort will fail to compile when T is a built-in 
type. The second drawback is that the use of this style in lib2 effectively 
"reserves" names in any namespace which defines types which may eventually be 
used with lib2. This may seem innocuous at first when applied to names like 
swap, but consider more ambiguous names like unique_copy() instead. It is easy 
to imagine the user wanting to define these names differently in his own 
namespace. A definition with semantics incompatible with the standard library 
could cause serious problems (see issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#225">225</A>).</P>
<P>Why, you may ask, can't we just partially specialize std::swap()? It's 
because the language doesn't allow for partial specialization of function 
templates. If you write:</P>
<BLOCKQUOTE><PRE>namespace std
{
    template &lt;class T&gt;
    void swap(lib1::big_int&lt;T&gt;&amp;, lib1::big_int&lt;T&gt;&amp;);
}</PRE></BLOCKQUOTE>
<P>You have just overloaded std::swap, which is illegal under the current 
language rules. On the other hand, the following full specialization is 
legal:</P>
<BLOCKQUOTE><PRE>namespace std
{
    template &lt;&gt;
    void swap(lib1::other_type&amp;, lib1::other_type&amp;);
}</PRE></BLOCKQUOTE>
<P>This issue reflects concerns raised by the "Namespace issue with specialized 
swap" thread on comp.lang.c++.moderated. A similar set of concerns was earlier 
raised on the boost.org mailing list and the ACCU-general mailing list. Also see 
library reflector message c++std-lib-7354.</P>
<P>J. C. van Winkel points out (in c++std-lib-9565) another unexpected fact: 
it's impossible to output a container of std::pair's using copy and an 
ostream_iterator, as long as both pair-members are built-in or std:: types. 
That's because a user-defined operator&lt;&lt; for (for example) 
std::pair&lt;const std::string, int&gt; will not be found: lookup for 
operator&lt;&lt; will be performed only in namespace std. Opinions differed on 
whether or not this was a defect, and, if so, whether the defect is that 
something is wrong with user-defined functionality and std, or whether it's that 
the standard library does not provide an operator&lt;&lt; for std::pair&lt;&gt;. 
</P>
<P><B>Proposed resolution:</B></P>
<P>Informally: introduce a Swappable concept, and specify that the value types 
of the iterators passed to certain standard algorithms (such as iter_swap, 
swap_ranges, reverse, rotate, and sort) conform to that concept. The Swappable 
concept will make it clear that these algorithms use unqualified lookup for the 
calls to <TT>swap</TT>. Also, in 26.3.3.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.valarray.transcend">[lib.valarray.transcend]</A> 
paragraph 1, state that the valarray transcendentals use unqualified lookup.</P>
<P><I>[Tokyo: Summary, "There is no conforming way to extend std::swap for user 
defined templates."&nbsp; The LWG agrees that there is a problem.&nbsp; Would 
like more information before proceeding. This may be a core issue. Core issue 
229 has been opened to discuss the core aspects of this problem. It was also 
noted that submissions regarding this issue have been received from several 
sources, but too late to be integrated into the issues list. ]</I></P>
<P><I>[Post-Tokyo: A paper with several proposed resolutions, 
J16/00-0029==WG21/N1252, "Shades of namespace std functions " by Alan Griffiths, 
is in the Post-Tokyo mailing. It should be considered a part of this 
issue.]</I></P>
<P><I>[Toronto: Dave Abrahams and Peter Dimov have proposed a resolution that 
involves core changes: it would add partial specialization of function template. 
The Core Working Group is reluctant to add partial specialization of function 
templates. It is viewed as a large change, CWG believes that proposal presented 
leaves some syntactic issues unanswered; if the CWG does add partial 
specialization of function templates, it wishes to develop its own proposal. The 
LWG continues to believe that there is a serious problem: there is no good way 
for users to force the library to use user specializations of generic standard 
library functions, and in certain cases (e.g. transcendental functions called by 
<TT>valarray</TT> and <TT>complex</TT>) this is important. Koenig lookup isn't 
adequate, since names within the library must be qualified with <TT>std</TT> 
(see issue 225), specialization doesn't work (we don't have partial 
specialization of function templates), and users aren't permitted to add 
overloads within namespace std. ]</I></P>
<P><I>[Copenhagen: Discussed at length, with no consensus. Relevant papers in 
the pre-Copenhagen mailing: N1289, N1295, N1296. Discussion focused on four 
options. (1) Relax restrictions on overloads within namespace std. (2) Mandate 
that the standard library use unqualified calls for <TT>swap</TT> and possibly 
other functions. (3) Introduce helper class templates for <TT>swap</TT> and 
possibly other functions. (4) Introduce partial specialization of function 
templates. Every option had both support and opposition. Straw poll (first 
number is support, second is strongly opposed): (1) 6, 4; (2) 6, 7; (3) 3, 8; 
(4) 4, 4.]</I></P>
<P><I>[Redmond: Discussed, again no consensus. Herb presented an argument that a 
user who is defining a type <TT>T</TT> with an associated <TT>swap</TT> should 
not be expected to put that <TT>swap</TT> in namespace std, either by 
overloading or by partial specialization. The argument is that <TT>swap</TT> is 
part of <TT>T</TT>'s interface, and thus should to in the same namespace as 
<TT>T</TT> and only in that namespace. If we accept this argument, the 
consequence is that standard library functions should use unqualified call of 
<TT>swap</TT>. (And which other functions? Any?) A small group (Nathan, Howard, 
Jeremy, Dave, Matt, Walter, Marc) will try to put together a proposal before the 
next meeting.]</I></P>
<P><I>[Curaao: An LWG-subgroup spent an afternoon working on issues 225, 226, 
and 229. Their conclusion was that the issues should be separated into an LWG 
portion (Howard's paper, N1387=02-0045), and a EWG portion (Dave will write a 
proposal). The LWG and EWG had (separate) discussions of this plan the next day. 
The proposed resolution is the one proposed by Howard.]</I></P>
<P><I>[Santa Cruz: the LWG agreed with the general direction of Howard's paper, 
N1387. (Roughly: Koenig lookup is disabled unless we say otherwise; this issue 
is about when we do say otherwise.) However, there were concerns about wording. 
Howard will provide new wording. Bill and Jeremy will review it.]</I></P>
<HR>
<A name=229>
<H3>229.&nbsp;Unqualified references of other library entities</H3></A>
<P><B>Section:</B>&nbsp;17.4.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.contents">[lib.contents]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A>&nbsp; 
<B>Submitter:</B>&nbsp;Steve Clamage&nbsp; <B>Date:</B>&nbsp;19 Apr 2000</P>
<P>Throughout the library chapters, the descriptions of library entities refer 
to other library entities without necessarily qualifying the names.</P>
<P>For example, section 25.2.2 "Swap" describes the effect of swap_ranges in 
terms of the unqualified name "swap". This section could reasonably be 
interpreted to mean that the library must be implemented so as to do a lookup of 
the unqualified name "swap", allowing users to override any ::std::swap function 
when Koenig lookup applies.</P>
<P>Although it would have been best to use explicit qualification with "::std::" 
throughout, too many lines in the standard would have to be adjusted to make 
that change in a Technical Corrigendum.</P>
<P>Issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#182">182</A>, which 
addresses qualification of <TT>size_t</TT>, is a special case of this. </P>
<P><B>Proposed resolution:</B></P>
<P>To section 17.4.1.1 "Library contents" Add the following paragraph:</P>
<BLOCKQUOTE>
  <P>Whenever a name x defined in the standard library is mentioned, the name x 
  is assumed to be fully qualified as ::std::x, unless explicitly described 
  otherwise. For example, if the Effects section for library function F is 
  described as calling library function G, the function ::std::G is 
meant.</P></BLOCKQUOTE>
<P><I>[Post-Tokyo: Steve Clamage submitted this issue at the request of the LWG 
to solve a problem in the standard itself similar to the problem within 
implementations of library identified by issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#225">225</A>. Any 
resolution of issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#225">225</A> should be 
coordinated with the resolution of this issue.]</I></P>
<P><I>[post-Toronto: Howard is undecided about whether it is appropriate for all 
standard library function names referred to in other standard library functions 
to be explicitly qualified by <TT>std</TT>: it is common advice that users 
should define global functions that operate on their class in the same namespace 
as the class, and this requires argument-dependent lookup if those functions are 
intended to be called by library code. Several LWG members are concerned that 
valarray appears to require argument-dependent lookup, but that the wording may 
not be clear enough to fall under "unless explicitly described 
otherwise".]</I></P>
<P><I>[Curaao: An LWG-subgroup spent an afternoon working on issues 225, 226, 
and 229. Their conclusion was that the issues should be separated into an LWG 
portion (Howard's paper, N1387=02-0045), and a EWG portion (Dave will write a 
proposal). The LWG and EWG had (separate) discussions of this plan the next day. 
This paper resolves issues 225 and 226. In light of that resolution, the 
proposed resolution for the current issue makes sense.]</I></P>
<HR>
<A name=231>
<H3>231.&nbsp;Precision in iostream?</H3></A>
<P><B>Section:</B>&nbsp;22.2.2.2.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.facet.num.put.virtuals">[lib.facet.num.put.virtuals]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A>&nbsp; 
<B>Submitter:</B>&nbsp;James Kanze, Stephen Clamage&nbsp; <B>Date:</B>&nbsp; 25 
Apr 2000</P>
<P>What is the following program supposed to output?</P><PRE>#include &lt;iostream&gt;

    int
    main()
    {
        std::cout.setf( std::ios::scientific , std::ios::floatfield ) ;
        std::cout.precision( 0 ) ;
        std::cout &lt;&lt; 1.00 &lt;&lt; '\n' ;
        return 0 ;
    }</PRE>
<P>From my C experience, I would expect "1e+00"; this is what <TT>printf("%.0e" 
, 1.00 );</TT> does. G++ outputs "1.000000e+00".</P>
<P>The only indication I can find in the standard is 22.2.2.2.2/11, where it 
says "For conversion from a floating-point type, if (flags &amp; fixed) != 0 or 
if str.precision() &gt; 0, then str.precision() is specified in the conversion 
specification." This is an obvious error, however, fixed is not a mask for a 
field, but a value that a multi-bit field may take -- the results of and'ing 
fmtflags with ios::fixed are not defined, at least not if ios::scientific has 
been set. G++'s behavior corresponds to what might happen if you do use (flags 
&amp; fixed) != 0 with a typical implementation (floatfield == 3 &lt;&lt; 
something, fixed == 1 &lt;&lt; something, and scientific == 2 &lt;&lt; 
something).</P>
<P>Presumably, the intent is either (flags &amp; floatfield) != 0, or (flags 
&amp; floatfield) == fixed; the first gives something more or less like the 
effect of precision in a printf floating point conversion. Only more or less, of 
course. In order to implement printf formatting correctly, you must know whether 
the precision was explicitly set or not. Say by initializing it to -1, instead 
of 6, and stating that for floating point conversions, if precision &lt; -1, 6 
will be used, for fixed point, if precision &lt; -1, 1 will be used, etc. Plus, 
of course, if precision == 0 and flags &amp; floatfield == 0, 1 should be = 
used. But it probably isn't necessary to emulate all of the anomalies of 
printf:-).</P>
<P><B>Proposed resolution:</B></P>
<P>Replace 22.2.2.2.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.facet.num.put.virtuals">[lib.facet.num.put.virtuals]</A>, 
paragraph 11, with the following sentence: </P>
<BLOCKQUOTE>For conversion from a floating-point type, 
  <TT><I>str</I>.precision()</TT> is specified in the conversion specification. 
</BLOCKQUOTE>
<P><B>Rationale:</B></P>
<P>The floatfield determines whether numbers are formatted as if with %f, %e, or 
%g. If the <TT>fixed</TT> bit is set, it's %f, if <TT>scientific</TT> it's %e, 
and if both bits are set, or neither, it's %g.</P>
<P>Turning to the C standard, a precision of 0 is meaningful for %f and %e. For 
%g, precision 0 is taken to be the same as precision 1.</P>
<P>The proposed resolution has the effect that if neither <TT>fixed</TT> nor 
<TT>scientific</TT> is set we'll be specifying a precision of 0, which will be 
internally turned into 1. There's no need to call it out as a special case.</P>
<P>The output of the above program will be "1e+00".</P>
<P><I>[Post-Curaao: Howard provided improved wording covering the case where 
precision is 0 and mode is %g.]</I></P>
<HR>
<A name=233>
<H3>233.&nbsp;Insertion hints in associative containers</H3></A>
<P><B>Section:</B>&nbsp;23.1.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-containers.html#lib.associative.reqmts">[lib.associative.reqmts]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Andrew Koenig&nbsp; <B>Date:</B>&nbsp;30 Apr 2000</P>
<P>If <TT>mm</TT> is a multimap and <TT>p</TT> is an iterator into the multimap, 
then <TT>mm.insert(p, x)</TT> inserts <TT>x</TT> into <TT>mm</TT> with 
<TT>p</TT> as a hint as to where it should go. Table 69 claims that the 
execution time is amortized constant if the insert winds up taking place 
adjacent to <TT>p</TT>, but does not say when, if ever, this is guaranteed to 
happen. All it says it that <TT>p</TT> is a hint as to where to insert. </P>
<P>The question is whether there is any guarantee about the relationship between 
<TT>p</TT> and the insertion point, and, if so, what it is. </P>
<P>I believe the present state is that there is no guarantee: The user can 
supply <TT>p</TT>, and the implementation is allowed to disregard it entirely. 
</P>
<P><B>Additional comments from Nathan:</B><BR>The vote [in Redmond] was on 
whether to elaborately specify the use of the hint, or to require behavior only 
if the value could be inserted adjacent to the hint. I would like to ensure that 
we have a chance to vote for a deterministic treatment: "before, if possible, 
otherwise after, otherwise anywhere appropriate", as an alternative to the 
proposed "before or after, if possible, otherwise [...]". </P>
<P><B>Proposed resolution:</B></P>
<P>In table 69 "Associative Container Requirements" in 23.1.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-containers.html#lib.associative.reqmts">[lib.associative.reqmts]</A>, 
in the row for <TT>a.insert(p, t)</TT>, change</P>
<BLOCKQUOTE>iterator p is a hint pointing to where the insert should start to 
  search. </BLOCKQUOTE>
<P>to</P>
<BLOCKQUOTE>insertion adjacent to iterator p is preferred if more than one 
  insertion point is valid. </BLOCKQUOTE>
<P>and change</P>
<BLOCKQUOTE>logarithmic in general, but amortized constant if t is inserted 
  right after p. </BLOCKQUOTE>
<P>to</P>
<BLOCKQUOTE>logarithmic in general, but amortized constant if t is inserted 
  adjacent to iterator p. </BLOCKQUOTE>
<P><I>[Toronto: there was general agreement that this is a real defect: when 
inserting an element x into a multiset that already contains several copies of 
x, there is no way to know whether the hint will be used. The proposed 
resolution was that the new element should always be inserted as close to the 
hint as possible. So, for example, if there is a subsequence of equivalent 
values, then providing a.begin() as the hint means that the new element should 
be inserted before the subsequence even if a.begin() is far away. JC van Winkel 
supplied precise wording for this proposed resolution, and also for an 
alternative resolution in which hints are only used when they are adjacent to 
the insertion point.]</I></P>
<P><I>[Copenhagen: the LWG agreed to the original proposed resolution, in which 
an insertion hint would be used even when it is far from the insertion point. 
This was contingent on seeing a reference implementation showing that it is 
possible to implement this requirement without loss of efficiency. John Potter 
provided such a reference implementation.]</I></P>
<P><I>[Redmond: The LWG was reluctant to adopt the proposal that emerged from 
Copenhagen: it seemed excessively complicated, and went beyond fixing the defect 
that we identified in Toronto. PJP provided the new wording described in this 
issue. Nathan agrees that we shouldn't adopt the more detailed semantics, and 
notes: "we know that you can do it efficiently enough with a red-black tree, but 
there are other (perhaps better) balanced tree techniques that might differ 
enough to make the detailed semantics hard to satisfy."]</I></P>
<P><I>[Curaao: Nathan should give us the alternative wording he suggests so the 
LWG can decide between the two options.]</I></P>
<HR>
<A name=247>
<H3>247.&nbsp;<TT>vector</TT>, <TT>deque::insert</TT> complexity</H3></A>
<P><B>Section:</B>&nbsp;23.2.4.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-containers.html#lib.vector.modifiers">[lib.vector.modifiers]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Lisa Lippincott&nbsp; <B>Date:</B>&nbsp;06 June 2000</P>
<P>Paragraph 2 of 23.2.4.3 [lib.vector.modifiers] describes the complexity of 
<TT>vector::insert</TT>:</P>
<BLOCKQUOTE>Complexity: If first and last are forward iterators, bidirectional 
  iterators, or random access iterators, the complexity is linear in the number 
  of elements in the range [first, last) plus the distance to the end of the 
  vector. If they are input iterators, the complexity is proportional to the 
  number of elements in the range [first, last) times the distance to the end of 
  the vector. </BLOCKQUOTE>
<P>First, this fails to address the non-iterator forms of <TT>insert</TT>.</P>
<P>Second, the complexity for input iterators misses an edge case -- it requires 
that an arbitrary number of elements can be added at the end of a 
<TT>vector</TT> in constant time.</P>
<P>At the risk of strengthening the requirement, I suggest simply</P>
<BLOCKQUOTE>Complexity: The complexity is linear in the number of elements 
  inserted plus the distance to the end of the vector. </BLOCKQUOTE>
<P>For input iterators, one may achieve this complexity by first inserting at 
the end of the <TT>vector</TT>, and then using <TT>rotate</TT>.</P>
<P>I looked to see if <TT>deque</TT> had a similar problem, and was surprised to 
find that <TT>deque</TT> places no requirement on the complexity of inserting 
multiple elements (23.2.1.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-containers.html#lib.deque.modifiers">[lib.deque.modifiers]</A>, 
paragraph 3):</P>
<BLOCKQUOTE>Complexity: In the worst case, inserting a single element into a 
  deque takes time linear in the minimum of the distance from the insertion 
  point to the beginning of the deque and the distance from the insertion point 
  to the end of the deque. Inserting a single element either at the beginning or 
  end of a deque always takes constant time and causes a single call to the copy 
  constructor of T. </BLOCKQUOTE>
<P>I suggest:</P>
<BLOCKQUOTE>Complexity: The complexity is linear in the number of elements 
  inserted plus the shorter of the distances to the beginning and end of the 
  deque. Inserting a single element at either the beginning or the end of a 
  deque causes a single call to the copy constructor of T. </BLOCKQUOTE>
<P><B>Proposed resolution:</B></P>
<P><I>[Toronto: It's agreed that there is a defect in complexity of 
multi-element insert for vector and deque. For vector, the complexity should 
probably be something along the lines of <TT>c<SUB>1</SUB> * N + c<SUB>2</SUB> * 
distance(i, end())</TT>. However, there is some concern about whether it is 
reasonable to amortize away the copies that we get from a reallocation whenever 
we exceed the vector's capacity. For deque, the situation is somewhat less 
clear. Deque is notoriously complicated, and we may not want to impose 
complexity requirements that would imply any implementation technique more 
complicated than a while loop whose body is a single-element insert.]</I></P>
<HR>
<A name=253>
<H3>253.&nbsp;valarray helper functions are almost entirely useless</H3></A>
<P><B>Section:</B>&nbsp;26.3.2.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.valarray.cons">[lib.valarray.cons]</A>, 
26.3.2.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.valarray.assign">[lib.valarray.assign]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Review">Review</A>&nbsp; 
<B>Submitter:</B>&nbsp;Robert Klarer&nbsp; <B>Date:</B>&nbsp;31 Jul 2000</P>
<P>This discussion is adapted from message c++std-lib-7056 posted November 11, 
1999. I don't think that anyone can reasonably claim that the problem described 
below is NAD.</P>
<P>These valarray constructors can never be called:</P><PRE>   template &lt;class T&gt;
         valarray&lt;T&gt;::valarray(const slice_array&lt;T&gt; &amp;);
   template &lt;class T&gt;
         valarray&lt;T&gt;::valarray(const gslice_array&lt;T&gt; &amp;);
   template &lt;class T&gt;
         valarray&lt;T&gt;::valarray(const mask_array&lt;T&gt; &amp;);
   template &lt;class T&gt;
         valarray&lt;T&gt;::valarray(const indirect_array&lt;T&gt; &amp;);
</PRE>
<P>Similarly, these valarray assignment operators cannot be called:</P><PRE>     template &lt;class T&gt;
     valarray&lt;T&gt; valarray&lt;T&gt;::operator=(const slice_array&lt;T&gt; &amp;);
     template &lt;class T&gt;
     valarray&lt;T&gt; valarray&lt;T&gt;::operator=(const gslice_array&lt;T&gt; &amp;);
     template &lt;class T&gt;
     valarray&lt;T&gt; valarray&lt;T&gt;::operator=(const mask_array&lt;T&gt; &amp;);
     template &lt;class T&gt;
     valarray&lt;T&gt; valarray&lt;T&gt;::operator=(const indirect_array&lt;T&gt; &amp;);
</PRE>
<P>Please consider the following example:</P><PRE>   #include &lt;valarray&gt;
   using namespace std;

   int main()
   {
       valarray&lt;double&gt; va1(12);
       valarray&lt;double&gt; va2(va1[slice(1,4,3)]); // line 1
   }
</PRE>
<P>Since the valarray va1 is non-const, the result of the sub-expression 
va1[slice(1,4,3)] at line 1 is an rvalue of type const 
std::slice_array&lt;double&gt;. This slice_array rvalue is then used to 
construct va2. The constructor that is used to construct va2 is declared like 
this:</P><PRE>     template &lt;class T&gt;
     valarray&lt;T&gt;::valarray(const slice_array&lt;T&gt; &amp;);
</PRE>
<P>Notice the constructor's const reference parameter. When the constructor is 
called, a slice_array must be bound to this reference. The rules for binding an 
rvalue to a const reference are in 8.5.3, paragraph 5 (see also 13.3.3.1.4). 
Specifically, paragraph 5 indicates that a second slice_array rvalue is 
constructed (in this case copy-constructed) from the first one; it is this 
second rvalue that is bound to the reference parameter. Paragraph 5 also 
requires that the constructor that is used for this purpose be callable, 
regardless of whether the second rvalue is elided. The copy-constructor in this 
case is not callable, however, because it is private. Therefore, the compiler 
should report an error.</P>
<P>Since slice_arrays are always rvalues, the valarray constructor that has a 
parameter of type const slice_array&lt;T&gt; &amp; can never be called. The same 
reasoning applies to the three other constructors and the four assignment 
operators that are listed at the beginning of this post. Furthermore, since 
these functions cannot be called, the valarray helper classes are almost 
entirely useless.</P>
<P><B>Proposed resolution:</B></P>
<P>slice_array:</P>
<UL>
  <LI>Make the copy constructor and copy-assignment operator declarations public 
  in the slice_array class template definition in 26.3.5 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.template.slice.array">[lib.template.slice.array]</A> 

  <LI>remove paragraph 3 of 26.3.5 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.template.slice.array">[lib.template.slice.array]</A> 

  <LI>remove the copy constructor declaration from 26.3.5.1 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.cons.slice.arr">[lib.cons.slice.arr]</A> 

  <LI>change paragraph 1 of 26.3.5.1 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.cons.slice.arr">[lib.cons.slice.arr]</A> 
  to read "This constructor is declared to be private. This constructor need not 
  be defined." 
  <LI>remove the first sentence of paragraph 1 of 26.3.5.2 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.slice.arr.assign">[lib.slice.arr.assign]</A> 

  <LI>Change the first three words of the second sentence of paragraph 1 of 
  26.3.5.2 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.slice.arr.assign">[lib.slice.arr.assign]</A> 
  to "These assignment operators have" </LI></UL>
<P>gslice_array:</P>
<UL>
  <LI>Make the copy constructor and copy-assignment operator declarations public 
  in the gslice_array class template definition in 26.3.7 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.template.gslice.array">[lib.template.gslice.array]</A> 

  <LI>remove the note in paragraph 3 of 26.3.7 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.template.gslice.array">[lib.template.gslice.array]</A> 

  <LI>remove the copy constructor declaration from 26.3.7.1 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.gslice.array.cons">[lib.gslice.array.cons]</A> 

  <LI>change paragraph 1 of 26.3.7.1 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.gslice.array.cons">[lib.gslice.array.cons]</A> 
  to read "This constructor is declared to be private. This constructor need not 
  be defined." 
  <LI>remove the first sentence of paragraph 1 of 26.3.7.2 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.gslice.array.assign">[lib.gslice.array.assign]</A> 

  <LI>Change the first three words of the second sentence of paragraph 1 of 
  26.3.7.2 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.gslice.array.assign">[lib.gslice.array.assign]</A> 
  to "These assignment operators have" </LI></UL>
<P>mask_array:</P>
<UL>
  <LI>Make the copy constructor and copy-assignment operator declarations public 
  in the mask_array class template definition in 26.3.8 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.template.mask.array">[lib.template.mask.array]</A> 

  <LI>remove the note in paragraph 2 of 26.3.8 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.template.mask.array">[lib.template.mask.array]</A> 

  <LI>remove the copy constructor declaration from 26.3.8.1 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.mask.array.cons">[lib.mask.array.cons]</A> 

  <LI>change paragraph 1 of 26.3.8.1 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.mask.array.cons">[lib.mask.array.cons]</A> 
  to read "This constructor is declared to be private. This constructor need not 
  be defined." 
  <LI>remove the first sentence of paragraph 1 of 26.3.8.2 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.mask.array.assign">[lib.mask.array.assign]</A> 

  <LI>Change the first three words of the second sentence of paragraph 1 of 
  26.3.8.2 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.mask.array.assign">[lib.mask.array.assign]</A> 
  to "These assignment operators have" </LI></UL>
<P>indirect_array:</P>
<UL>
  <LI>Make the copy constructor and copy-assignment operator declarations public 
  in the indirect_array class definition in 26.3.9 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.template.indirect.array">[lib.template.indirect.array]</A> 

  <LI>remove the note in paragraph 2 of 26.3.9 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.template.indirect.array">[lib.template.indirect.array]</A> 

  <LI>remove the copy constructor declaration from 26.3.9.1 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.indirect.array.cons">[lib.indirect.array.cons]</A> 

  <LI>change the descriptive text in 26.3.9.1 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.indirect.array.cons">[lib.indirect.array.cons]</A> 
  to read "This constructor is declared to be private. This constructor need not 
  be defined." 
  <LI>remove the first sentence of paragraph 1 of 26.3.9.2 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.indirect.array.assign">[lib.indirect.array.assign]</A> 

  <LI>Change the first three words of the second sentence of paragraph 1 of 
  26.3.9.2 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.indirect.array.assign">[lib.indirect.array.assign]</A> 
  to "These assignment operators have" </LI></UL>
<P><I>[Proposed resolution was modified in Santa Cruz: explicitly make copy 
constructor and copy assignment operators public, instead of removing 
them.]</I></P>
<P><B>Rationale:</B></P>
<P>Keeping the valarray constructors private is untenable. Merely making 
valarray a friend of the helper classes isn't good enough, because access to the 
copy constructor is checked in the user's environment.</P>
<P>Making the assignment operator public is not strictly necessary to solve this 
problem. A majority of the LWG <I>(straw poll: 13-4)</I> believed we should make 
the assignment operators public, in addition to the copy constructors, for 
reasons of symmetry and user expectation.</P>
<HR>
<A name=258>
<H3>258.&nbsp;Missing allocator requirement</H3></A>
<P><B>Section:</B>&nbsp;20.1.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-utilities.html#lib.allocator.requirements">[lib.allocator.requirements]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Matt Austern&nbsp; <B>Date:</B>&nbsp;22 Aug 2000</P>
<P>From lib-7752: </P>
<P>I've been assuming (and probably everyone else has been assuming) that 
allocator instances have a particular property, and I don't think that property 
can be deduced from anything in Table 32. </P>
<P>I think we have to assume that allocator type conversion is a homomorphism. 
That is, if x1 and x2 are of type X, where X::value_type is T, and if type Y is 
X::template rebind&lt;U&gt;::other, then Y(x1) == Y(x2) if and only if x1 == x2. 
</P>
<P>Further discussion: Howard Hinnant writes, in lib-7757: </P>
<P>I think I can prove that this is not provable by Table 32. And I agree it 
needs to be true except for the "and only if". If x1 != x2, I see no reason why 
it can't be true that Y(x1) == Y(x2). Admittedly I can't think of a practical 
instance where this would happen, or be valuable. But I also don't see a need to 
add that extra restriction. I think we only need: </P>
<BLOCKQUOTE>if (x1 == x2) then Y(x1) == Y(x2) </BLOCKQUOTE>
<P>If we decide that == on allocators is transitive, then I think I can prove 
the above. But I don't think == is necessarily transitive on allocators. That 
is: </P>
<P>Given x1 == x2 and x2 == x3, this does not mean x1 == x3. </P>
<P>Example:</P>
<BLOCKQUOTE>
  <P>x1 can deallocate pointers from: x1, x2, x3 <BR>x2 can deallocate pointers 
  from: x1, x2, x4 <BR>x3 can deallocate pointers from: x1, x3 <BR>x4 can 
  deallocate pointers from: x2, x4 </P>
  <P>x1 == x2, and x2 == x4, but x1 != x4 </P></BLOCKQUOTE>
<P><B>Proposed resolution:</B></P>
<P><I>[Toronto: LWG members offered multiple opinions. One opinion is that it 
should not be required that <TT>x1 == x2</TT> implies <TT>Y(x1) == Y(x2)</TT>, 
and that it should not even be required that <TT>X(x1) == x1</TT>. Another 
opinion is that the second line from the bottom in table 32 already implies the 
desired property. This issue should be considered in light of other issues 
related to allocator instances.]</I></P>
<HR>
<A name=278>
<H3>278.&nbsp;What does iterator validity mean?</H3></A>
<P><B>Section:</B>&nbsp;23.2.2.4 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-containers.html#lib.list.ops">[lib.list.ops]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A>&nbsp; 
<B>Submitter:</B>&nbsp;P.J. Plauger&nbsp; <B>Date:</B>&nbsp;27 Nov 2000</P>
<P>Section 23.2.2.4 [lib.list.ops] states that </P><PRE>  void splice(iterator position, list&lt;T, Allocator&gt;&amp; x);
</PRE>
<P><I>invalidates</I> all iterators and references to list <TT>x</TT>. </P>
<P>But what does the C++ Standard mean by "invalidate"? You can still 
dereference the iterator to a spliced list element, but you'd better not use it 
to delimit a range within the original list. For the latter operation, it has 
definitely lost some of its validity. </P>
<P>If we accept the proposed resolution to issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#250">250</A>, then we'd 
better clarify that a "valid" iterator need no longer designate an element 
within the same container as it once did. We then have to clarify what we mean 
by invalidating a past-the-end iterator, as when a vector or string grows by 
reallocation. Clearly, such an iterator has a different kind of validity. 
Perhaps we should introduce separate terms for the two kinds of "validity." </P>
<P><B>Proposed resolution:</B></P>
<P>Add the following text to the end of section 24.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.iterator.requirements">[lib.iterator.requirements]</A>, 
after paragraph 5:</P>
<BLOCKQUOTE>An <I>invalid</I> iterator is an iterator that may be singular. 
  [Footnote: This definition applies to pointers, since pointers are iterators. 
  The effect of dereferencing an iterator that has been invalidated is 
  undefined.] </BLOCKQUOTE>
<P><I>[post-Copenhagen: Matt provided wording.]</I></P>
<P><I>[Redmond: General agreement with the intent, some objections to the 
wording. Dave provided new wording.]</I></P>
<P><B>Rationale:</B></P>
<P>This resolution simply defines a term that the Standard uses but never 
defines, "invalid", in terms of a term that is defined, "singular".</P>
<P>Why do we say "may be singular", instead of "is singular"? That's becuase a 
valid iterator is one that is known to be nonsingular. Invalidating an iterator 
means changing it in such a way that it's no longer known to be nonsingular. An 
example: inserting an element into the middle of a vector is correctly said to 
invalidate all iterators pointing into the vector. That doesn't necessarily mean 
they all become singular.</P>
<HR>
<A name=280>
<H3>280.&nbsp;Comparison of reverse_iterator to const reverse_iterator</H3></A>
<P><B>Section:</B>&nbsp;24.4.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.reverse.iterators">[lib.reverse.iterators]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Steve Cleary&nbsp; <B>Date:</B>&nbsp;27 Nov 2000</P>
<P>This came from an email from Steve Cleary to Fergus in reference to issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#179">179</A>. The 
library working group briefly discussed this in Toronto and believed it should 
be a separate issue. There was also some reservations about whether this was a 
worthwhile problem to fix. </P>
<P>Steve said: "Fixing reverse_iterator. std::reverse_iterator can (and should) 
be changed to preserve these additional requirements." He also said in email 
that it can be done without breaking user's code: "If you take a look at my 
suggested solution, reverse_iterator doesn't have to take two parameters; there 
is no danger of breaking existing code, except someone taking the address of one 
of the reverse_iterator global operator functions, and I have to doubt if anyone 
has ever done that. . . <I>But</I>, just in case they have, you can leave the 
old global functions in as well -- they won't interfere with the 
two-template-argument functions. With that, I don't see how <I>any</I> user code 
could break." </P>
<P><B>Proposed resolution:</B></P>
<P><B>Section:</B> 24.4.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.reverse.iterator">[lib.reverse.iterator]</A> 
add/change the following declarations:</P><PRE>  A) Add a templated assignment operator, after the same manner
        as the templated copy constructor, i.e.:

  template &lt; class U &gt;
  reverse_iterator &lt; Iterator &gt;&amp; operator=(const reverse_iterator&lt; U &gt;&amp; u);

  B) Make all global functions (except the operator+) have
  two template parameters instead of one, that is, for
  operator ==, !=, &lt;, &gt;, &lt;=, &gt;=, - replace:

       template &lt; class Iterator &gt;
       typename reverse_iterator&lt; Iterator &gt;::difference_type operator-(
                 const reverse_iterator&lt; Iterator &gt;&amp; x,
                 const reverse_iterator&lt; Iterator &gt;&amp; y);

  with:

      template &lt; class Iterator1, class Iterator2 &gt;
      typename reverse_iterator &lt; Iterator1 &gt;::difference_type operator-(
                 const reverse_iterator &lt; Iterator1 &gt; &amp; x,
                 const reverse_iterator &lt; Iterator2 &gt; &amp; y);
</PRE>
<P>Also make the addition/changes for these signatures in 24.4.1.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.reverse.iter.ops">[lib.reverse.iter.ops]</A>. 
</P>
<P><I>[ Copenhagen: The LWG is concerned that the proposed resolution introduces 
new overloads. Experience shows that introducing overloads is always risky, and 
that it would be inappropriate to make this change without implementation 
experience. It may be desirable to provide this feature in a different way. 
]</I></P>
<HR>
<A name=282>
<H3>282.&nbsp;What types does numpunct grouping refer to?</H3></A>
<P><B>Section:</B>&nbsp;22.2.2.2.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.facet.num.put.virtuals">[lib.facet.num.put.virtuals]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A>&nbsp; 
<B>Submitter:</B>&nbsp;Howard Hinnant&nbsp; <B>Date:</B>&nbsp;5 Dec 2000</P>
<P>Paragraph 16 mistakenly singles out integral types for inserting 
thousands_sep() characters. This conflicts with the syntax for floating point 
numbers described under 22.2.3.1/2. </P>
<P><B>Proposed resolution:</B></P>
<P>Change paragraph 16 from:</P>
<BLOCKQUOTE>For integral types, punct.thousands_sep() characters are inserted 
  into the sequence as determined by the value returned by punct.do_grouping() 
  using the method described in 22.2.3.1.2 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.facet.numpunct.virtuals">[lib.facet.numpunct.virtuals]</A>. 
</BLOCKQUOTE>
<P>To:</P>
<BLOCKQUOTE>For arithmetic types, punct.thousands_sep() characters are 
  inserted into the sequence as determined by the value returned by 
  punct.do_grouping() using the method described in 22.2.3.1.2 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.facet.numpunct.virtuals">[lib.facet.numpunct.virtuals]</A>. 
</BLOCKQUOTE>
<P><I>[ Copenhagen: Opinions were divided about whether this is actually an 
inconsistency, but at best it seems to have been unintentional. This is only an 
issue for floating-point output: The standard is unambiguous that 
implementations must parse thousands_sep characters when performing 
floating-point. The standard is also unambiguous that this requirement does not 
apply to the "C" locale. ]</I></P>
<P><I>[ A survey of existing practice is needed; it is believed that some 
implementations do insert thousands_sep characters for floating-point output and 
others fail to insert thousands_sep characters for floating-point input even 
though this is unambiguously required by the standard. ]</I></P>
<P><I>[Post-Curaao: the above proposed resolution is the consensus of Howard, 
Bill, Pete, Benjamin, Nathan, Dietmar, Boris, and Martin.]</I></P>
<HR>
<A name=283>
<H3>283.&nbsp;std::replace() requirement incorrect/insufficient</H3></A>
<P><B>Section:</B>&nbsp;25.2.4 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-algorithms.html#lib.alg.replace">[lib.alg.replace]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Review">Review</A>&nbsp; 
<B>Submitter:</B>&nbsp;Martin Sebor&nbsp; <B>Date:</B>&nbsp;15 Dec 2000</P>
<P>(revision of the further discussion) There are a number of problems with the 
requires clauses for the algorithms in 25.1 and 25.2. The requires clause of 
each algorithm should describe the necessary and sufficient requirements on the 
inputs to the algorithm such that the algorithm compiles and runs properly. Many 
of the requires clauses fail to do this. Here is a summary of the kinds of 
mistakes: </P>
<OL>
  <LI>Use of EqualityComparable, which only puts requirements on a single type, 
  when in fact an equality operator is required between two different types, 
  typically either T and the iterator's value type or between the value types of 
  two different iterators. 
  <LI>Use of Assignable for T when in fact what was needed is Assignable for the 
  value_type of the iterator, and convertability from T to the value_type of the 
  iterator. Or for output iterators, the requirement should be that T is 
  writable to the iterator (output iterators do not have value types). </LI></OL>
<P>Here is the list of algorithms that contain mistakes: </P>
<UL>
  <LI>25.1.2 std::find 
  <LI>25.1.6 std::count 
  <LI>25.1.8 std::equal 
  <LI>25.1.9 std::search, std::search_n 
  <LI>25.2.4 std::replace, std::replace_copy 
  <LI>25.2.5 std::fill 
  <LI>25.2.7 std::remove, std::remove_copy </LI></UL>
<P>Also, in the requirements for EqualityComparable, the requirement that the 
operator be defined for const objects is lacking. </P>
<P><B>Proposed resolution:</B></P>
<P>20.1.1 Change p1 from</P>
<P>In Table 28, <TT>T</TT> is a type to be supplied by a C++ program 
instantiating a template, <TT>a</TT>, <TT>b</TT>, and <TT>c</TT> are values of 
type <TT>T</TT>. </P>
<P>to</P>
<P>In Table 28, <TT>T</TT> is a type to be supplied by a C++ program 
instantiating a template, <TT>a</TT>, <TT>b</TT>, and <TT>c</TT> are values of 
type <TT>const T</TT>. </P>
<P>25 Between p8 and p9</P>
<P>Add the following sentence:</P>
<P>When the description of an algorithm gives an expression such as <TT>*first 
== value</TT> for a condition, it is required that the expression evaluate to 
either true or false in boolean contexts.</P>
<P>25.1.2 Change p1 by deleting the requires clause.</P>
<P>25.1.6 Change p1 by deleting the requires clause.</P>
<P>25.1.9</P>
<P>Change p4 from</P>
<P>-4- Requires: Type <TT>T</TT> is <TT>EqualityComparable</TT> (20.1.1), type 
Size is convertible to integral type (4.7.12.3). </P>
<P>to</P>
<P>-4- Requires: The type <TT>Size</TT> is convertible to integral type 
(4.7.12.3).</P>
<P>25.2.4 Change p1 from</P>
<P>-1- Requires: Type <TT>T</TT> is <TT>Assignable</TT> (23.1 ) (and, for 
<TT>replace()</TT>, <TT>EqualityComparable</TT> (20.1.1 )).</P>
<P>to</P>
<P>-1- Requires: The expression <TT>*first = new_value</TT> must be valid.</P>
<P>and change p4 from</P>
<P>-4- Requires: Type <TT>T</TT> is <TT>Assignable</TT> (23.1) (and, for 
<TT>replace_copy()</TT>, <TT>EqualityComparable</TT> (20.1.1)). The ranges 
<TT>[first, last)</TT> and <TT>[result, result + (last - first))</TT> shall not 
overlap.</P>
<P>to</P>
<P>-4- Requires: The results of the expressions <TT>*first</TT> and 
<TT>new_value</TT> must be writable to the result output iterator. The ranges 
<TT>[first, last)</TT> and <TT>[result, result + (last - first))</TT> shall not 
overlap.</P>
<P>25.2.5 Change p1 from</P>
<P>-1- Requires: Type <TT>T</TT> is <TT>Assignable</TT> (23.1). The type 
<TT>Size</TT> is convertible to an integral type (4.7.12.3).</P>
<P>to</P>
<P>-1- Requires: The expression <TT>value</TT> must be is writable to the output 
iterator. The type <TT>Size</TT> is convertible to an integral type 
(4.7.12.3).</P>
<P>25.2.7 Change p1 from</P>
<P>-1- Requires: Type <TT>T</TT> is <TT>EqualityComparable</TT> (20.1.1).</P>
<P>to</P>
<P>-1- Requires: The value type of the iterator must be <TT>Assignable</TT> 
(23.1). </P>
<P><B>Rationale:</B></P>
<P>The general idea of the proposed solution is to remove the faulty requires 
clauses and let the returns and effects clauses speak for themselves. That is, 
the returns clauses contain expressions that must be valid, and therefore 
already imply the correct requirements. In addition, a sentence is added at the 
beginning of chapter 25 saying that expressions given as conditions must 
evaluate to true or false in a boolean context. An alternative would be to say 
that the type of these condition expressions must be literally bool, but that 
would be imposing a greater restriction that what the standard currently says 
(which is convertible to bool). </P>
<HR>
<A name=290>
<H3>290.&nbsp;Requirements to for_each and its function object</H3></A>
<P><B>Section:</B>&nbsp;25.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-algorithms.html#lib.alg.foreach">[lib.alg.foreach]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Angelika Langer&nbsp; <B>Date:</B>&nbsp;03 Jan 2001</P>
<P>The specification of the for_each algorithm does not have a "Requires" 
section, which means that there are no restrictions imposed on the function 
object whatsoever. In essence it means that I can provide any function object 
with arbitrary side effects and I can still expect a predictable result. In 
particular I can expect that the function object is applied exactly last - first 
times, which is promised in the "Complexity" section. </P>
<P>I don't see how any implementation can give such a guarantee without imposing 
requirements on the function object. </P>
<P>Just as an example: consider a function object that removes elements from the 
input sequence. In that case, what does the complexity guarantee (applies f 
exactly last - first times) mean? </P>
<P>One can argue that this is obviously a nonsensical application and a 
theoretical case, which unfortunately it isn't. I have seen programmers shooting 
themselves in the foot this way, and they did not understand that there are 
restrictions even if the description of the algorithm does not say so. </P>
<P><B>Proposed resolution:</B></P>
<P>Add a "Requires" section to section 25.1.1 similar to those proposed for 
transform and the numeric algorithms (see issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#242">242</A>): </P>
<BLOCKQUOTE>-2- <B>Requires</B>: In the range [first, last], f shall not 
  invalidate iterators or subranges. </BLOCKQUOTE>
<P><I>[Copenhagen: The LWG agrees that a function object passed to an algorithm 
should not invalidate iterators in the range that the algorithm is operating on. 
The LWG believes that this should be a blanket statement in Clause 25, not just 
a special requirement for <TT>for_each</TT>. ]</I></P>
<HR>
<A name=291>
<H3>291.&nbsp;Underspecification of set algorithms</H3></A>
<P><B>Section:</B>&nbsp;25.3.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-algorithms.html#lib.alg.set.operations">[lib.alg.set.operations]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Review">Review</A>&nbsp; 
<B>Submitter:</B>&nbsp;Matt Austern&nbsp; <B>Date:</B>&nbsp;03 Jan 2001</P>
<P>The standard library contains four algorithms that compute set operations on 
sorted ranges: <TT>set_union</TT>, <TT>set_intersection</TT>, 
<TT>set_difference</TT>, and <TT>set_symmetric_difference</TT>. Each of these 
algorithms takes two sorted ranges as inputs, and writes the output of the 
appropriate set operation to an output range. The elements in the output range 
are sorted. </P>
<P>The ordinary mathematical definitions are generalized so that they apply to 
ranges containing multiple copies of a given element. Two elements are 
considered to be "the same" if, according to an ordering relation provided by 
the user, neither one is less than the other. So, for example, if one input 
range contains five copies of an element and another contains three, the output 
range of <TT>set_union</TT> will contain five copies, the output range of 
<TT>set_intersection</TT> will contain three, the output range of 
<TT>set_difference</TT> will contain two, and the output range of 
<TT>set_symmetric_difference</TT> will contain two. </P>
<P>Because two elements can be "the same" for the purposes of these set 
algorithms, without being identical in other respects (consider, for example, 
strings under case-insensitive comparison), this raises a number of unanswered 
questions: </P>
<UL>
  <LI>If we're copying an element that's present in both of the input ranges, 
  which one do we copy it from? 
  <LI>If there are <I>n</I> copies of an element in the relevant input range, 
  and the output range will contain fewer copies (say <I>m</I>) which ones do we 
  choose? The first <I>m</I>, or the last <I>m</I>, or something else? 
  <LI>Are these operations stable? That is, does a run of equivalent elements 
  appear in the output range in the same order as as it appeared in the input 
  range(s)? </LI></UL>
<P>The standard should either answer these questions, or explicitly say that the 
answers are unspecified. I prefer the former option, since, as far as I know, 
all existing implementations behave the same way. </P>
<P><B>Proposed resolution:</B></P>
<P>Add the following to the end of 25.3.5.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-algorithms.html#lib.set.union">[lib.set.union]</A> 
paragraph 5:</P>
<BLOCKQUOTE>If [first1, last1) contains <I>m</I> elements that are equivalent 
  to each other and [first2, last2) contains <I>n</I> elements that are 
  equivalent to them, then max(<I>m</I>, <I>n</I>) of these elements will be 
  copied to the output range: all <I>m</I> of these elements from [first1, 
  last1), and the last max(<I>n-m</I>, 0) of them from [first2, last2), in that 
  order. </BLOCKQUOTE>
<P>Add the following to the end of 25.3.5.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-algorithms.html#lib.set.intersection">[lib.set.intersection]</A> 
paragraph 5:</P>
<BLOCKQUOTE>If [first1, last1) contains <I>m</I> elements that are equivalent 
  to each other and [first2, last2) contains <I>n</I> elements that are 
  equivalent to them, the first min(<I>m</I>, <I>n</I>) of those elements from 
  [first1, last1) are copied to the output range. </BLOCKQUOTE>
<P>Add a new paragraph, <B>Notes</B>, after 25.3.5.4 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-algorithms.html#lib.set.difference">[lib.set.difference]</A> 
paragraph 4:</P>
<BLOCKQUOTE>If [first1, last1) contains <I>m</I> elements that are equivalent 
  to each other and [first2, last2) contains <I>n</I> elements that are 
  equivalent to them, the last max(<I>m-n</I>, 0) elements from [first1, last1) 
  are copied to the output range. </BLOCKQUOTE>
<P>Add a new paragraph, <B>Notes</B>, after 25.3.5.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-algorithms.html#lib.set.symmetric.difference">[lib.set.symmetric.difference]</A> 
paragraph 4:</P>
<BLOCKQUOTE>If [first1, last1) contains <I>m</I> elements that are equivalent 
  to each other and [first2, last2) contains <I>n</I> elements that are 
  equivalent to them, then |<I>m - n</I>| of those elements will be copied to 
  the output range: the last <I>m - n</I> of these elements from [first1, last1) 
  if <I>m</I> &gt; <I>n</I>, and the last <I>n - m</I> of these elements from 
  [first2, last2) if <I>m</I> &lt; <I>n</I>. </BLOCKQUOTE>
<P><I>[Santa Cruz: it's believed that this language is clearer than what's in 
the Standard. However, it's also believed that the Standard may already make 
these guarantees (although not quite in these words). Bill and Howard will check 
and see whether they think that some or all of these changes may be redundant. 
If so, we may close this issue as NAD.]</I></P>
<P><B>Rationale:</B></P>
<P>For simple cases, these descriptions are equivalent to what's already in the 
Standard. For more complicated cases, they describe the behavior of existing 
implementations.</P>
<HR>
<A name=294>
<H3>294.&nbsp;User defined macros and standard headers</H3></A>
<P><B>Section:</B>&nbsp;17.4.3.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.macro.names">[lib.macro.names]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;James Kanze&nbsp; <B>Date:</B>&nbsp;11 Jan 2001</P>
<P>Paragraph 2 of 17.4.3.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.macro.names">[lib.macro.names]</A> 
reads: "A translation unit that includes a header shall not contain any macros 
that define names declared in that header." As I read this, it would mean that 
the following program is legal:</P><PRE>  #define npos 3.14
  #include &lt;sstream&gt;
</PRE>
<P>since npos is not defined in &lt;sstream&gt;. It is, however, defined in 
&lt;string&gt;, and it is hard to imagine an implementation in which 
&lt;sstream&gt; didn't include &lt;string&gt;.</P>
<P>I think that this phrase was probably formulated before it was decided that a 
standard header may freely include other standard headers. The phrase would be 
perfectly appropriate for C, for example. In light of 17.4.4.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.res.on.headers">[lib.res.on.headers]</A> 
paragraph 1, however, it isn't stringent enough.</P>
<P><B>Proposed resolution:</B></P>
<P>In paragraph 2 of 17.4.3.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.macro.names">[lib.macro.names]</A>, 
change "A translation unit that includes a header shall not contain any macros 
that define names declared in that header." to "A translation unit that includes 
a header shall not contain any macros that define names declared in any standard 
header."</P>
<P><I>[Copenhagen: the general idea is clearly correct, but there is concern 
about making sure that the two paragraphs in 17.4.3.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.macro.names">[lib.macro.names]</A> 
remain consistent. Nathan will provide new wording.]</I></P>
<HR>
<A name=299>
<H3>299.&nbsp;Incorrect return types for iterator dereference</H3></A>
<P><B>Section:</B>&nbsp;24.1.4 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.bidirectional.iterators">[lib.bidirectional.iterators]</A>, 
24.1.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.random.access.iterators">[lib.random.access.iterators]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;John Potter&nbsp; <B>Date:</B>&nbsp;22 Jan 2001</P>
<P>In section 24.1.4 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.bidirectional.iterators">[lib.bidirectional.iterators]</A>, 
Table 75 gives the return type of *r-- as convertible to T. This is not 
consistent with Table 74 which gives the return type of *r++ as T&amp;. *r++ = t 
is valid while *r-- = t is invalid. </P>
<P>In section 24.1.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.random.access.iterators">[lib.random.access.iterators]</A>, 
Table 76 gives the return type of a[n] as convertible to T. This is not 
consistent with the semantics of *(a + n) which returns T&amp; by Table 74. *(a 
+ n) = t is valid while a[n] = t is invalid. </P>
<P>Discussion from the Copenhagen meeting: the first part is uncontroversial. 
The second part, operator[] for Random Access Iterators, requires more thought. 
There are reasonable arguments on both sides. Return by value from operator[] 
enables some potentially useful iterators, e.g. a random access "iota iterator" 
(a.k.a "counting iterator" or "int iterator"). There isn't any obvious way to do 
this with return-by-reference, since the reference would be to a temporary. On 
the other hand, <TT>reverse_iterator</TT> takes an arbitrary Random Access 
Iterator as template argument, and its operator[] returns by reference. If we 
decided that the return type in Table 76 was correct, we would have to change 
<TT>reverse_iterator</TT>. This change would probably affect user code. </P>
<P>History: the contradiction between <TT>reverse_iterator</TT> and the Random 
Access Iterator requirements has been present from an early stage. In both the 
STL proposal adopted by the committee (N0527==94-0140) and the STL technical 
report (HPL-95-11 (R.1), by Stepanov and Lee), the Random Access Iterator 
requirements say that operator[]'s return value is "convertible to T". In N0527 
reverse_iterator's operator[] returns by value, but in HPL-95-11 (R.1), and in 
the STL implementation that HP released to the public, reverse_iterator's 
operator[] returns by reference. In 1995, the standard was amended to reflect 
the contents of HPL-95-11 (R.1). The original intent for operator[] is unclear. 
</P>
<P>In the long term it may be desirable to add more fine-grained iterator 
requirements, so that access method and traversal strategy can be decoupled. 
(See "Improved Iterator Categories and Requirements", N1297 = 01-0011, by Jeremy 
Siek.) Any decisions about issue 299 should keep this possibility in mind. </P>
<P><B>Proposed resolution:</B></P>
<P>In section 24.1.4 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.bidirectional.iterators">[lib.bidirectional.iterators]</A>, 
change the return type in table 75 from "convertible to T" to T&amp;.</P>
<P>In section 24.1.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.random.access.iterators">[lib.random.access.iterators]</A>, 
change the return type in table 76 from "convertible to T" to T&amp;.</P>
<P><I>[Curaao: Jeremy volunteered to work on this issue.]</I></P>
<P><B>Rationale:</B></P>
<P>This proposed resolution is a compromise between John Potter's resolution, 
which requires <TT>T&amp;</TT> as the return type of <TT>a[n]</TT>, and the 
current wording, which requires convertible to <TT>T</TT>. The compromise is to 
keep the convertible to <TT>T</TT> for the return type of the expression 
<TT>a[n]</TT>, but to also add <TT>a[n] = t</TT> as a valid expression. This 
compromise "saves" the common case uses of random access iterators, while at the 
same time allowing iterators such as counting iterator and caching file 
iterators to remain random access iterators (iterators where the lifetime of the 
object returned by <TT>operator*()</TT> is tied to the lifetime of the 
iterator). </P>
<P>Note there is one kind of mutable random access iterator that will no longer 
meet the new requirements. Currently, iterators that return an r-value from 
<TT>operator[]</TT> meet the requirements for a mutable random access iterartor, 
even though the expression <TT>a[n] = t</TT> will only modify a temporary that 
goes away. With this proposed resolution, <TT>a[n] = t</TT> will be required to 
have the same operational semantics as <TT>*(a + n) = t</TT>. </P>
<P>Note also that <TT>reverse_iterator</TT> (24.4.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.reverse.iterators">[lib.reverse.iterators]</A>) 
may be broken. However, this proposed resolution doesn't break it any worse than 
it already is. This is a separate issue. (Issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#386">386</A>.)</P>
<HR>
<A name=300>
<H3>300.&nbsp;list::merge() specification incomplete</H3></A>
<P><B>Section:</B>&nbsp;23.2.2.4 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-containers.html#lib.list.ops">[lib.list.ops]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A>&nbsp; 
<B>Submitter:</B>&nbsp;John Pedretti&nbsp; <B>Date:</B>&nbsp;23 Jan 2001</P>
<P>The "Effects" clause for list::merge() (23.2.2.4, p23) appears to be 
incomplete: it doesn't cover the case where the argument list is identical to 
*this (i.e., this == &amp;x). The requirement in the note in p24 (below) is that 
x be empty after the merge which is surely unintended in this case. </P>
<P><B>Proposed resolution:</B></P>
<P>In 23.2.2.4 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-containers.html#lib.list.ops">[lib.list.ops]</A>, 
replace paragraps 23-25 with:</P>
<BLOCKQUOTE>
  <P>23 Effects: if (&amp;x == this) does nothing; otherwise, merges the two 
  sorted ranges [begin(), end()) and [x.begin(), x.end()). The result is a range 
  in which the elements will be sorted in non-decreasing order according to the 
  ordering defined by comp; that is, for every iterator i in the range other 
  than the first, the condition comp(*i, *(i - 1)) will be false. </P>
  <P>24 Notes: Stable: if (&amp;x != this), then for equivalent elements in the 
  two original ranges, the elements from the original range [begin(), end()) 
  always precede the elements from the original range [x.begin(), x.end()). If 
  (&amp;x != this) the range [x.begin(), x.end()) is empty after the merge. </P>
  <P>25 Complexity: At most size() + x.size() - 1 applications of comp if 
  (&amp;x ! = this); otherwise, no applications of comp are performed. If an 
  exception is thrown other than by a comparison there are no effects. 
</P></BLOCKQUOTE>
<P><I>[Copenhagen: The original proposed resolution did not fix all of the 
problems in 23.2.2.4 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-containers.html#lib.list.ops">[lib.list.ops]</A>, 
p22-25. Three different paragraphs (23, 24, 25) describe the effects of 
<TT>merge</TT>. Changing p23, without changing the other two, appears to 
introduce contradictions. Additionally, "merges the argument list into the list" 
is excessively vague.]</I></P>
<P><I>[Post-Curaao: Robert Klarer provided new wording.]</I></P>
<HR>
<A name=309>
<H3>309.&nbsp;Does sentry catch exceptions?</H3></A>
<P><B>Section:</B>&nbsp;27.6 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.iostream.format">[lib.iostream.format]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Martin Sebor&nbsp; <B>Date:</B>&nbsp;19 Mar 2001</P>
<P>The descriptions of the constructors of basic_istream&lt;&gt;::sentry 
(27.6.1.1.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.istream::sentry">[lib.istream::sentry]</A>) 
and basic_ostream&lt;&gt;::sentry (27.6.2.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.ostream::sentry">[lib.ostream::sentry]</A>) 
do not explain what the functions do in case an exception is thrown while they 
execute. Some current implementations allow all exceptions to propagate, others 
catch them and set ios_base::badbit instead, still others catch some but let 
others propagate. </P>
<P>The text also mentions that the functions may call setstate(failbit) (without 
actually saying on what object, but presumably the stream argument is meant). 
That may have been fine for basic_istream&lt;&gt;::sentry prior to issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#195">195</A>, since the 
function performs an input operation which may fail. However, issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#195">195</A> amends 
27.6.1.1.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.istream::sentry">[lib.istream::sentry]</A>, 
p2 to clarify that the function should actually call setstate(failbit | eofbit), 
so the sentence in p3 is redundant or even somewhat contradictory. </P>
<P>The same sentence that appears in 27.6.2.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.ostream::sentry">[lib.ostream::sentry]</A>, 
p3 doesn't seem to be very meaningful for basic_istream&lt;&gt;::sentry which 
performs no input. It is actually rather misleading since it would appear to 
guide library implementers to calling setstate(failbit) when 
os.tie()-&gt;flush(), the only called function, throws an exception (typically, 
it's badbit that's set in response to such an event). </P>
<P><B>Proposed resolution:</B></P>
<P>Add the following paragraph immediately after 27.6.1.1.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.istream::sentry">[lib.istream::sentry]</A>, 
p5</P>
<BLOCKQUOTE>
  <P>If an exception is thrown during the preparation then ios::badbit is turned 
  on* in is's error state. </P>
  <P>[Footnote: This is done without causing an ios::failure to be thrown. --- 
  end footnote] </P>
  <P>If (is.exceptions() &amp; ios_base::badbit)!= 0 then the exception is 
  rethrown. </P></BLOCKQUOTE>
<P>And strike the following sentence from 27.6.1.1.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.istream::sentry">[lib.istream::sentry]</A>, 
p5</P>
<BLOCKQUOTE>During preparation, the constructor may call setstate(failbit) 
  (which may throw ios_base::failure (lib.iostate.flags)) </BLOCKQUOTE>
<P>Add the following paragraph immediately after 27.6.2.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.ostream::sentry">[lib.ostream::sentry]</A>, 
p3</P>
<BLOCKQUOTE>
  <P>If an exception is thrown during the preparation then ios::badbit is turned 
  on* in os's error state. </P>
  <P>[Footnote: This is done without causing an ios::failure to be thrown. --- 
  end footnote] </P>
  <P>If (os.exceptions() &amp; ios_base::badbit)!= 0 then the exception is 
  rethrown. </P></BLOCKQUOTE>
<P>And strike the following sentence from 27.6.2.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.ostream::sentry">[lib.ostream::sentry]</A>, 
p3</P>
<BLOCKQUOTE>During preparation, the constructor may call setstate(failbit) 
  (which may throw ios_base::failure (lib.iostate.flags)) </BLOCKQUOTE>
<P>(Note that the removal of the two sentences means that the ctors will not be 
able to report the failure of any implementation-dependent operations referred 
to in footnotes 280 and 293, unless such operations throw an exception.)</P>
<P><I>[ Copenhagen: It was agreed that there was an issue here, but there was 
disagreement about the resolution. Some LWG members argued that a sentry's 
constructor should not catch exceptions, because sentries should only be used 
within (un)formatted input functions and that exception handling is the 
responsibility of those functions, not of the sentries. ]</I></P>
<HR>
<A name=336>
<H3>336.&nbsp;Clause 17 lack of references to deprecated headers</H3></A>
<P><B>Section:</B>&nbsp;17 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.library">[lib.library]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A>&nbsp; 
<B>Submitter:</B>&nbsp;Detlef Vollmann&nbsp; <B>Date:</B>&nbsp;05 Sep 2001</P>
<P>From c++std-edit-873:</P>
<P>17.4.1.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.headers">[lib.headers]</A>, 
Table 11. In this table, the header &lt;strstream&gt; is missing.</P>
<P>This shows a general problem: The whole clause 17 refers quite often to 
clauses 18 through 27, but D.7 is also a part of the standard library (though a 
deprecated one).</P>
<P><B>Proposed resolution:</B></P>
<P>To 17.4.1.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.headers">[lib.headers]</A> 
Table 11, C++ Library Headers, add "&lt;strstream&gt;".</P>
<P>In the following places, change "clauses 17 through 27" to "clauses 17 
through 27 and Annex D":</P>
<UL>
  <LI>1.2 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/intro.html#intro.refs">[intro.refs]</A> 
  Normative references/1/footnote 1 
  <LI>1.3 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/intro.html#intro.defs">[intro.defs]</A> 
  Definitions/1 
  <LI>7 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/dcl.html#dcl.dcl">[dcl.dcl]</A> Library 
  introduction/9 
  <LI>17.3 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.description">[lib.description]</A> 
  Method of description (Informative)/1 
  <LI>17.3.2.1.3 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.character.seq">[lib.character.seq]</A> 
  Character sequences/1/bullet 2 
  <LI>17.3.2.2 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.functions.within.classes">[lib.functions.within.classes]</A> 
  Functions within classes/1 
  <LI>17.3.2.3 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.objects.within.classes">[lib.objects.within.classes]</A> 
  Private members/1/(2 places) 
  <LI>17.4 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.requirements">[lib.requirements]</A> 
  Library-wide requirements/1 
  <LI>17.4.1.2 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.headers">[lib.headers]</A> 
  Headers/4 
  <LI>17.4.3.4 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.replacement.functions">[lib.replacement.functions]</A> 
  Replacement functions/1 
  <LI>17.4.4.3 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.global.functions">[lib.global.functions]</A> 
  Global or non-member functions/2 
  <LI>17.4.4.6 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.protection.within.classes">[lib.protection.within.classes]</A> 
  Protection within classes/1 </LI></UL>
<HR>
<A name=342>
<H3>342.&nbsp;seek and eofbit</H3></A>
<P><B>Section:</B>&nbsp;27.6.1.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.istream.unformatted">[lib.istream.unformatted]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Howard Hinnant&nbsp; <B>Date:</B>&nbsp;09 Oct 201</P>
<P>I think we have a defect.</P>
<P>According to lwg issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#60">60</A> which is now 
a dr, the description of seekg in 27.6.1.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.istream.unformatted">[lib.istream.unformatted]</A> 
paragraph 38 now looks like:</P>
<BLOCKQUOTE>Behaves as an unformatted input function (as described in 
  27.6.1.3, paragraph 1), except that it does not count the number of characters 
  extracted and does not affect the value returned by subsequent calls to 
  gcount(). After constructing a sentry object, if fail() != true, executes 
  rdbuf()&shy;&gt;pubseekpos( pos). </BLOCKQUOTE>
<P>And according to lwg issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#243">243</A> which is 
also now a dr, 27.6.1.3, paragraph 1 looks like:</P>
<BLOCKQUOTE>Each unformatted input function begins execution by constructing 
  an object of class sentry with the default argument noskipws (second) argument 
  true. If the sentry object returns true, when converted to a value of type 
  bool, the function endeavors to obtain the requested input. Otherwise, if the 
  sentry constructor exits by throwing an exception or if the sentry object 
  returns false, when converted to a value of type bool, the function returns 
  without attempting to obtain any input. In either case the number of extracted 
  characters is set to 0; unformatted input functions taking a character array 
  of non-zero size as an argument shall also store a null character (using 
  charT()) in the first location of the array. If an exception is thrown during 
  input then ios::badbit is turned on in *this'ss error state. If 
  (exception()&amp;badbit)!= 0 then the exception is rethrown. It also counts 
  the number of characters extracted. If no exception has been thrown it ends by 
  storing the count in a member object and returning the value specified. In any 
  event the sentry object is destroyed before leaving the unformatted input 
  function. </BLOCKQUOTE>
<P>And finally 27.6.1.1.2/5 says this about sentry:</P>
<BLOCKQUOTE>If, after any preparation is completed, is.good() is true, ok_ != 
  false otherwise, ok_ == false. </BLOCKQUOTE>
<P>So although the seekg paragraph says that the operation proceeds if !fail(), 
the behavior of unformatted functions says the operation proceeds only if 
good(). The two statements are contradictory when only eofbit is set. I don't 
think the current text is clear which condition should be respected. </P>
<P><B>Further discussion from Redmond:</B></P>
<P>PJP: It doesn't seem quite right to say that <TT>seekg</TT> is "unformatted". 
That makes specific claims about sentry that aren't quite appropriate for 
seeking, which has less fragile failure modes than actual input. If we do really 
mean that it's unformatted input, it should behave the same way as other 
unformatted input. On the other hand, "principle of least surprise" is that 
seeking from EOF ought to be OK.</P>
<P>Dietmar: nothing should depend on eofbit. Eofbit should only be examined by 
the user to determine why something failed.</P>
<P><I>[Taken from c++std-lib-8873, c++std-lib-8874, c++std-lib-8876]</I></P>
<P><B>Proposed resolution:</B></P>
<P><I>[Santa Cruz: On the one hand, it would clearly be silly to seek to a 
non-EOF position without resetting eofbit. On the other hand, having seek clear 
eofbit explicitly would set a major precedent: there is currently <I>no</I> 
place where any of the flags are reset without the user explicitly asking for 
them to be. This is the tip of a general problem, that the various flags are 
stickier than many users might expect. Bill, Gaby, and Howard will discuss this 
issue and propose a resolution.]</I></P>
<HR>
<A name=347>
<H3>347.&nbsp;locale::category and bitmask requirements</H3></A>
<P><B>Section:</B>&nbsp;22.1.1.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.locale.category">[lib.locale.category]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Review">Review</A>&nbsp; 
<B>Submitter:</B>&nbsp;P.J. Plauger, Nathan Myers&nbsp; <B>Date:</B>&nbsp;23 Oct 
2001</P>
<P>In 22.1.1.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.locale.category">[lib.locale.category]</A> 
paragraph 1, the category members are described as bitmask elements. In fact, 
the bitmask requirements in 17.3.2.1.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.bitmask.types">[lib.bitmask.types]</A> 
don't seem quite right: <TT>none</TT> and <TT>all</TT> are bitmask constants, 
not bitmask elements.</P>
<P>In particular, the requirements for <TT>none</TT> interact poorly with the 
requirement that the LC_* constants from the C library must be recognizable as 
C++ locale category constants. LC_* values should not be mixed with these values 
to make category values.</P>
<P>We have two options for the proposed resolution. Informally: option 1 removes 
the requirement that LC_* values be recognized as category arguments. Option 2 
changes the category type so that this requirement is implementable, by allowing 
<TT>none</TT> to be some value such as 0x1000 instead of 0.</P>
<P>Nathan writes: "I believe my proposed resolution [Option 2] merely 
re-expresses the status quo more clearly, without introducing any changes beyond 
resolving the DR.</P>
<P><B>Proposed resolution:</B></P>
<P>Replace the first two paragraphs of 22.1.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.locale.types">[lib.locale.types]</A> 
with:</P>
<BLOCKQUOTE><PRE>    typedef int category;
</PRE>
  <P>Valid category values include the <TT>locale</TT> member bitmask elements 
  <TT>collate</TT>, <TT>ctype</TT>, <TT>monetary</TT>, <TT>numeric</TT>, 
  <TT>time</TT>, and <TT>messages</TT>, each of which represents a single locale 
  category. In addition, <TT>locale</TT> member bitmask constant <TT>none</TT> 
  is defined as zero and represents no category. And locale member bitmask 
  constant <TT>all</TT> is defined such that the expression</P><PRE>    (collate | ctype | monetary | numeric | time | messages | all) == all
</PRE>
  <P>is <TT>true</TT>, and represents the union of all categories. Further the 
  expression <TT>(X | Y)</TT>, where <TT>X</TT> and <TT>Y</TT> each represent a 
  single category, represents the union of the two categories. </P>
  <P><TT>locale</TT> member functions expecting a <TT>category</TT> argument 
  require one of the <TT>category</TT> values defined above, or the union of two 
  or more such values. Such a <TT>category</TT> argument identifies a set of 
  locale categories. Each locale category, in turn, identifies a set of locale 
  facets, including at least those shown in Table 51: </P></BLOCKQUOTE>
<P><I>[Curaao: need input from locale experts.]</I></P>
<P><B>Rationale:</B></P>
<P>The LWG considered, and rejected, an alternate proposal (described as "Option 
2" in the discussion). The main reason for rejecting it was that library 
implementors were concerened about implementation difficult, given that getting 
a C++ library to work smoothly with a separately written C library is already a 
delicate business. Some library implementers were also concerned about the issue 
of adding extra locale categories.</P>
<BLOCKQUOTE>
  <P><B>Option 2:</B> <BR>Replace the first paragraph of 22.1.1.1 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.locale.types">[lib.locale.types]</A> 
  with:</P>
  <BLOCKQUOTE>
    <P>Valid category values include the enumerated values. In addition, the 
    result of applying commutative operators | and &amp; to any two valid values 
    is valid, and results in the setwise union and intersection, respectively, 
    of the argument categories. The values <TT>all</TT> and <TT>none</TT> are 
    defined such that for any valid value <TT>cat</TT>, the expressions <TT>(cat 
    | all == all)</TT>, <TT>(cat &amp; all == cat)</TT>, <TT>(cat | none == 
    cat)</TT> and <TT>(cat &amp; none == none)</TT> are true. For non-equal 
    values <TT>cat1</TT> and <TT>cat2</TT> of the remaining enumerated values, 
    <TT>(cat1 &amp; cat2 == none)</TT> is true. For any valid categories 
    <TT>cat1</TT> and <TT>cat2</TT>, the result of <TT>(cat1 &amp; ~cat2)</TT> 
    is valid, and equals the setwise union of those categories found in 
    <TT>cat1</TT> but not found in <TT>cat2</TT>. [Footnote: it is not required 
    that <TT>all</TT> equal the setwise union of the other enumerated values; 
    implementations may add extra categories.] </P></BLOCKQUOTE></BLOCKQUOTE>
<HR>
<A name=352>
<H3>352.&nbsp;missing fpos requirements</H3></A>
<P><B>Section:</B>&nbsp;21.1.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-strings.html#lib.char.traits.typedefs">[lib.char.traits.typedefs]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Review">Review</A>&nbsp; 
<B>Submitter:</B>&nbsp;Martin Sebor&nbsp; <B>Date:</B>&nbsp;2 Dec 2001</P>
<P><I>(1)</I> There are no requirements on the <TT>stateT</TT> template 
parameter of <TT>fpos</TT> listed in 27.4.3. The interface appears to require 
that the type be at least Assignable and CopyConstructible (27.4.3.1, p1), and I 
think also DefaultConstructible (to implement the operations in Table 88). </P>
<P>21.1.2, p3, however, only requires that 
<TT>char_traits&lt;charT&gt;::state_type</TT> meet the requirements of 
CopyConstructible types. </P>
<P><I>(2)</I> Additionally, the <TT>stateT</TT> template argument has no 
corresponding typedef in fpos which might make it difficult to use in generic 
code. </P>
<P><B>Proposed resolution:</B></P>
<P>Modify 21.1.2, p4 from </P>
<P>Requires: <TT>state_type</TT> shall meet the requirements of 
CopyConstructible types (20.1.3). </P>
<P>Requires: state_type shall meet the requirements of Assignable (23.1, p4), 
CopyConstructible (20.1.3), and DefaultConstructible (20.1.4) types. </P>
<P><B>Rationale:</B></P>
<P>The LWG feels this is two issues, as indicated above. The first is a 
defect---std::basic_fstream is unimplementable without these additional 
requirements---and the proposed resolution fixes it. The second is questionable; 
who would use that typedef? The class template fpos is used only in a very few 
places, all of which know the state type already. Unless motivation is provided, 
the second should be considered NAD.</P>
<HR>
<A name=355>
<H3>355.&nbsp;Operational semantics for a.back()</H3></A>
<P><B>Section:</B>&nbsp;23.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-containers.html#lib.sequence.reqmts">[lib.sequence.reqmts]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Yaroslav Mironov&nbsp; <B>Date:</B>&nbsp;23 Jan 2002</P>
<P>Table 68 "Optional Sequence Operations" in 23.1.1/12 specifies operational 
semantics for "a.back()" as "*--a.end()", which may be ill-formed <I>[because 
calling operator-- on a temporary (the return) of a built-in type is 
ill-formed]</I>, provided a.end() returns a simple pointer rvalue (this is 
almost always the case for std::vector::end(), for example). Thus, the 
specification is not only incorrect, it demonstrates a dangerous construct: 
"--a.end()" may successfully compile and run as intended, but after changing the 
type of the container or the mode of compilation it may produce compile-time 
error. </P>
<P><B>Proposed resolution:</B></P>
<P>Change the specification in table 68 "Optional Sequence Operations" in 
23.1.1/12 for "a.back()" from</P>
<BLOCKQUOTE>*--a.end() </BLOCKQUOTE>
<P>to</P>
<BLOCKQUOTE>
  <P>*a.rbegin()</P></BLOCKQUOTE>
<P>and the specification for "a.pop_back()" from</P>
<BLOCKQUOTE>a.erase(--a.end()) </BLOCKQUOTE>
<P>to</P>
<BLOCKQUOTE>
  <P>a.erase(rbegin())</P></BLOCKQUOTE>
<P><I>[Curaao: LWG changed PR from "{ X::iterator tmp = a.end(); return *--tmp; 
}" to "*a.rbegin()", and from "{ X::iterator tmp = a.end(); a.erase(--tmp); }" 
to "a.erase(rbegin())".]</I></P>
<P><I>[There is a second possible defect; table 68 "Optional Sequence 
Operations" in the "Operational Semantics" column uses operations present only 
in the "Reversible Container" requirements, yet there is no stated dependency 
between these separate requirements tables. Ask in Santa Cruz if the LWG would 
like a new issue opened.]</I></P>
<P><I>[Santa Cruz: the proposed resolution is even worse than what's in the 
current standard: erase is undefined for reverse iterator. If we're going to 
make the change, we need to define a temporary and use operator--. Additionally, 
we don't know how prevalent this is: do we need to make this change in more than 
one place? Martin has volunteered to review the standard and see if this problem 
occurs elsewhere.]</I></P>
<HR>
<A name=356>
<H3>356.&nbsp;Meaning of ctype_base::mask enumerators</H3></A>
<P><B>Section:</B>&nbsp;22.2.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.category.ctype">[lib.category.ctype]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Matt Austern&nbsp; <B>Date:</B>&nbsp;23 Jan 2002</P>
<P>What should the following program print?</P><PRE>  #include &lt;locale&gt;
  #include &lt;iostream&gt;

  class my_ctype : public std::ctype&lt;char&gt;
  {
    typedef std::ctype&lt;char&gt; base;
  public:
    my_ctype(std::size_t refs = 0) : base(my_table, false, refs)
    {
      std::copy(base::classic_table(), base::classic_table() + base::table_size,
                my_table);
      my_table[(unsigned char) '_'] = (base::mask) (base::print | base::space);
    }
  private:
    mask my_table[base::table_size];
  };

  int main()
  {
    my_ctype ct;
    std::cout &lt;&lt; "isspace: " &lt;&lt; ct.is(std::ctype_base::space, '_') &lt;&lt; "    "
              &lt;&lt; "isalpha: " &lt;&lt; ct.is(std::ctype_base::alpha, '_') &lt;&lt; std::endl;
  }
</PRE>
<P>The goal is to create a facet where '_' is treated as whitespace.</P>
<P>On gcc 3.0, this program prints "isspace: 1 isalpha: 0". On Microsoft C++ it 
prints "isspace: 1 isalpha: 1".</P>
<P>I believe that both implementations are legal, and the standard does not give 
enough guidance for users to be able to use std::ctype's protected interface 
portably.</P>
<P>The above program assumes that ctype_base::mask enumerators like 
<TT>space</TT> and <TT>print</TT> are disjoint, and that the way to say that a 
character is both a space and a printing character is to or those two 
enumerators together. This is suggested by the "exposition only" values in 
22.2.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.category.ctype">[lib.category.ctype]</A>, 
but it is nowhere specified in normative text. An alternative interpretation is 
that the more specific categories subsume the less specific. The above program 
gives the results it does on the Microsoft compiler because, on that compiler, 
<TT>print</TT> has all the bits set for each specific printing character class. 
</P>
<P>From the point of view of std::ctype's public interface, there's no important 
difference between these two techniques. From the point of view of the protected 
interface, there is. If I'm defining a facet that inherits from 
std::ctype&lt;char&gt;, I'm the one who defines the value that table()['a'] 
returns. I need to know what combination of mask values I should use. This isn't 
so very esoteric: it's exactly why std::ctype has a protected interface. If we 
care about users being able to write their own ctype facets, we have to give 
them a portable way to do it. </P>
<P>Related reflector messages: lib-9224, lib-9226, lib-9229, lib-9270, lib-9272, 
lib-9273, lib-9274, lib-9277, lib-9279. </P>
<P>Issue <A href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#339">339</A> 
is related, but not identical. The proposed resolution if issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-defects.html#339">339</A> says that 
ctype_base::mask must be a bitmask type. It does not say that the 
ctype_base::mask elements are bitmask elements, so it doesn't directly affect 
this issue.</P>
<P>More comments from Benjamin Kosnik, who believes that that C99 compatibility 
essentially requires what we're calling option 1 below.</P>
<BLOCKQUOTE><PRE>I think the C99 standard is clear, that isspace -&gt; !isalpha.
--------

#include &lt;locale&gt;
#include &lt;iostream&gt;

class my_ctype : public std::ctype&lt;char&gt;
{
private:
  typedef std::ctype&lt;char&gt; base;
  mask my_table[base::table_size];

public:
  my_ctype(std::size_t refs = 0) : base(my_table, false, refs)
  {
    std::copy(base::classic_table(), base::classic_table() + base::table_size,
              my_table);
    mask both = base::print | base::space;
    my_table[static_cast&lt;mask&gt;('_')] = both;
  }
};

int main()
{
  using namespace std;
  my_ctype ct;
  cout &lt;&lt; "isspace: " &lt;&lt; ct.is(ctype_base::space, '_') &lt;&lt; endl;
  cout &lt;&lt; "isprint: " &lt;&lt; ct.is(ctype_base::print, '_') &lt;&lt; endl;

  // ISO C99, isalpha iff upper | lower set, and !space.
  // 7.5, p 193
  // -&gt; looks like g++ behavior is correct.
  // 356 -&gt; bitmask elements are required for ctype_base
  // 339 -&gt; bitmask type required for mask
  cout &lt;&lt; "isalpha: " &lt;&lt; ct.is(ctype_base::alpha, '_') &lt;&lt; endl;
}
</PRE></BLOCKQUOTE>
<P><B>Proposed resolution:</B></P>
<P>Informally, we have three choices:</P>
<OL>
  <LI>Require that the enumerators are disjoint (except for alnum and graph) 
  <LI>Require that the enumerators are not disjoint, and specify which of them 
  subsume which others. (e.g. mandate that lower includes alpha and print) 
  <LI>Explicitly leave this unspecified, which the result that the above program 
  is not portable. </LI></OL>
<P>Either of the first two options is just as good from the standpoint of 
portability. Either one will require some implementations to change.</P>
<P><I>[ More discussion is needed. Nobody likes option 3. Options 1 and 2 are 
both controversial, 2 perhaps less so. Benjamin thinks that option 1 is required 
for C99 compatibility. ]</I></P>
<HR>
<A name=358>
<H3>358.&nbsp;interpreting <TT>thousands_sep</TT> after a <TT>decimal_point</TT> 
</H3></A>
<P><B>Section:</B>&nbsp;22.2.2.1.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.facet.num.get.virtuals">[lib.facet.num.get.virtuals]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A>&nbsp; 
<B>Submitter:</B>&nbsp;Martin Sebor&nbsp; <B>Date:</B>&nbsp;12 Mar 2002</P>
<P>I don't think <TT>thousands_sep</TT> is being treated correctly after 
decimal_point has been seen. Since grouping applies only to the integral part of 
the number, the first such occurrence should, IMO, terminate Stage 2. (If it 
does not terminate it, then 22.2.2.1.2, p12 and 22.2.3.1.2, p3 need to explain 
how <TT>thousands_sep</TT> is to be interpreted in the fractional part of a 
number.) </P>
<P>The easiest change I can think of that resolves this issue would be something 
like below. </P>
<P><B>Proposed resolution:</B></P>
<P>Change the first sentence of 22.2.2.1.2, p9 from </P>
<BLOCKQUOTE>If discard is true then the position of the character is 
  remembered, but the character is otherwise ignored. If it is not discarded, 
  then a check is made to determine if c is allowed as the next character of an 
  input field of the conversion specifier returned by stage 1. If so it is 
  accumulated. </BLOCKQUOTE>
<P>to</P>
<BLOCKQUOTE>If <TT>discard</TT> is true, then if <TT>'.'</TT> has not yet been 
  accumulated, then the position of the character is remembered, but the 
  character is otherwise ignored. Otherwise, if <TT>'.'</TT> has already been 
  accumulated, the character is discarded and Stage 2 terminates. ... 
</BLOCKQUOTE>
<P><B>Rationale:</B></P>
<P>We believe this reflects the intent of the Standard. Thousands sep characters 
after the decimal point are not useful in any locale. Some formatting 
conventions do group digits that follow the decimal point, but they usually 
introduce a different grouping character instead of reusing the thousand sep 
character. If we want to add support for such conventions, we need to do so 
explicitly.</P>
<HR>
<A name=359>
<H3>359.&nbsp;num_put&lt;&gt;::do_put (..., bool) undocumented</H3></A>
<P><B>Section:</B>&nbsp;22.2.2.2.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.facet.num.put.members">[lib.facet.num.put.members]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Review">Review</A>&nbsp; 
<B>Submitter:</B>&nbsp;Martin Sebor&nbsp; <B>Date:</B>&nbsp;12 Mar 2002</P>
<P>22.2.2.2.1, p1:</P><PRE>    iter_type put (iter_type out, ios_base&amp; str, char_type fill,
                   bool val) const;
    ...

    1   Returns: do_put (out, str, fill, val).
    </PRE>
<P>AFAICS, the behavior of do_put (..., bool) is not documented anywhere, 
however, 22.2.2.2.2, p23:</P>
<BLOCKQUOTE><PRE>iter_type put (iter_type out, ios_base&amp; str, char_type fill,
               bool val) const;
</PRE>Effects: If (str.flags() &amp; ios_base::boolalpha) == 0 then do out = 
  do_put(out, str, fill, (int)val) Otherwise do <PRE>             string_type s =
                 val ? use_facet&lt;ctype&lt;charT&gt; &gt;(loc).truename()
                     : use_facet&lt;ctype&lt;charT&gt; &gt;(loc).falsename();
</PRE>and then insert the characters of s into out. <I>out</I>. </BLOCKQUOTE>
<P>This means that the bool overload of <TT>do_put()</TT> will never be called, 
which contradicts the first paragraph. Perhaps the declaration should read 
<TT>do_put()</TT>, and not <TT>put()</TT>? </P>
<P>Note also that there is no <B>Returns</B> clause for this function, which 
should probably be corrected, just as should the second occurrence of 
<I>"out."</I> in the text. </P>
<P>I think the least invasive change to fix it would be something like the 
following: </P>
<P><B>Proposed resolution:</B></P>
<P>In 22.2.2.2.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.facet.num.put.virtuals">[lib.facet.num.put.virtuals]</A>, 
just above paragraph 1, remove the <TT>bool</TT> overload.</P>
<P>In 22.2.2.2.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.facet.num.put.virtuals">[lib.facet.num.put.virtuals]</A>, 
p23, make the following changes </P>
<BLOCKQUOTE>Replace <TT>put()</TT> with <TT>do_put()</TT> in the declaration 
  of the member function. </BLOCKQUOTE>
<BLOCKQUOTE>Change the <B>Effects</B> clause to a <B>Returns</B> clause (to 
  avoid the requirement to call <TT>do_put(..., int)</TT> from <TT>do_put (..., 
  bool))</TT> like so: </BLOCKQUOTE>
<BLOCKQUOTE>23 <B>Returns</B>: If <TT>(str.flags() &amp; ios_base::boolalpha) 
  == 0</TT> then <TT>do_put (out, str, fill, (long)val)</TT> Otherwise the 
  function obtains a string <TT>s</TT> as if by <PRE>             string_type s =
                val ? use_facet&lt;ctype&lt;charT&gt; &gt;(loc).truename()
                    : use_facet&lt;ctype&lt;charT&gt; &gt;(loc).falsename();
</PRE>and then inserts each character <TT>c</TT> of s into out via <TT>*out++ 
  = c</TT> and returns <TT>out</TT>. </BLOCKQUOTE>
<P><B>Rationale:</B></P>
<P>This fixes a couple of obvious typos, and also fixes what appears to be a 
requirement of gratuitous inefficiency. </P>
<HR>
<A name=360>
<H3>360.&nbsp;locale mandates inefficient implementation</H3></A>
<P><B>Section:</B>&nbsp;22.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.locale">[lib.locale]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A>&nbsp; 
<B>Submitter:</B>&nbsp;Martin Sebor&nbsp; <B>Date:</B>&nbsp;12 Mar 2002</P>
<P>22.1.1, p7 (copied below) allows iostream formatters and extractors to make 
assumptions about the values returned from facet members. However, such 
assumptions are apparently not guaranteed to hold in other cases (e.g., when the 
facet members are being called directly rather than as a result of iostream 
calls, or between successive calls to the same iostream functions with no 
interevening calls to <TT>imbue()</TT>, or even when the facet member functions 
are called from other member functions of other facets). This restriction 
prevents locale from being implemented efficiently. </P>
<P><B>Proposed resolution:</B></P>
<P>Change the first sentence in 22.1.1, p7 from</P>
<BLOCKQUOTE>In successive calls to a locale facet member function during a 
  call to an iostream inserter or extractor or a streambuf member function, the 
  returned result shall be identical. [Note: This implies that such results may 
  safely be reused without calling the locale facet member function again, and 
  that member functions of iostream classes cannot safely call <TT>imbue()</TT> 
  themselves, except as specified elsewhere. --end note] </BLOCKQUOTE>
<P>to</P>
<BLOCKQUOTE>In successive calls to a locale facet member function on a facet 
  object installed in the same locale, the returned result shall be identical. 
  ... </BLOCKQUOTE>
<P><B>Rationale:</B></P>
<P>This change is reasonable becuase it clarifies the intent of this part of the 
standard.</P>
<HR>
<A name=362>
<H3>362.&nbsp;bind1st/bind2nd type safety</H3></A>
<P><B>Section:</B>&nbsp;20.3.6.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-utilities.html#lib.bind.1st">[lib.bind.1st]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Andrew Demkin&nbsp; <B>Date:</B>&nbsp;26 Apr 2002</P>
<P>The definition of bind1st() (20.3.6.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-utilities.html#lib.bind.1st">[lib.bind.1st]</A>) 
can result in the construction of an unsafe binding between incompatible pointer 
types. For example, given a function whose first parameter type is 'pointer to 
T', it's possible without error to bind an argument of type 'pointer to U' when 
U does not derive from T: </P><PRE>   foo(T*, int);

   struct T {};
   struct U {};

   U u;

   int* p;
   int* q;

   for_each(p, q, bind1st(ptr_fun(foo), &amp;u));    // unsafe binding
</PRE>
<P>The definition of bind1st() includes a functional-style conversion to map its 
argument to the expected argument type of the bound function (see below): </P><PRE>  typename Operation::first_argument_type(x)
</PRE>
<P>A functional-style conversion (5.2.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/expr.html#expr.type.conv">[expr.type.conv]</A>) 
is defined to be semantically equivalent to an explicit cast expression (5.4 <A 
href="file:///P:/j16/33-pre-oxford/lwg/expr.html#expr.cast">[expr.cast]</A>), 
which may (according to 5.4, paragraph 5) be interpreted as a reinterpret_cast, 
thus masking the error. </P>
<P>The problem and proposed change also apply to 20.3.6.4 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-utilities.html#lib.bind.2nd">[lib.bind.2nd]</A>.</P>
<P><B>Proposed resolution:</B></P>
<P>The simplest and most localized change to prevent such errors is to require 
bind1st() use a static_cast expression rather than the functional-style 
conversion; that is, have bind1st() return: </P><PRE>   binder1st&lt;Operation&gt;( op,
     static_cast&lt;typename Operation::first_argument_type&gt;(x)).
</PRE>
<P>A more agressive solution is to change the semantics of functional-style 
conversions to not permit a reinterpret_cast. For contexts that require the 
semantics of reinterpret_cast, the language may want to require the use of an 
explicit cast expression such as '(T) x' or 'reinterpret_cast&lt;T&gt;(x)' and 
limit the behavior of the functional notation to match statically-checked and 
standard conversions (as defined by 5.2.9 and 4.10, etc.). Although changing the 
semantics of functional-style conversions may seem drastic and does have 
language-wide ramifications, it has the benefit of better unifying the 
conversion rules for user defined types and built-in types, which can be 
especially important for generic template programming. </P>
<P><I>[Santa Cruz: it's clear that a function-style cast is wrong. Maybe a 
static cast would be better, or maybe no cast at all. Jeremy will check with the 
original author of this part of the Standard and will see what the original 
intent was.]</I></P>
<HR>
<A name=363>
<H3>363.&nbsp;Missing exception specification in 27.4.2.1.1</H3></A>
<P><B>Section:</B>&nbsp;27.4.2.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.ios::failure">[lib.ios::failure]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A>&nbsp; 
<B>Submitter:</B>&nbsp;Walter Brown and Marc Paterno&nbsp; <B>Date:</B>&nbsp;20 
May 2002</P>
<P>The destructor of ios_base::failure should have an empty throw specification, 
because the destructor of its base class, exception, is declared in this way. 
</P>
<P><B>Proposed resolution:</B></P>
<P>Change the destructor to</P><PRE>  virtual ~failure() throw();
</PRE>
<P><B>Rationale:</B></P>
<P>Fixes an obvious glitch. This is almost editorial.</P>
<HR>
<A name=364>
<H3>364.&nbsp;Inconsistent wording in 27.5.2.4.2</H3></A>
<P><B>Section:</B>&nbsp;27.5.2.4.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.streambuf.virt.buffer">[lib.streambuf.virt.buffer]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A>&nbsp; 
<B>Submitter:</B>&nbsp;Walter Brown, Marc Paterno&nbsp; <B>Date:</B>&nbsp;10 May 
2002</P>
<P>27.5.2.4.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.streambuf.virt.buffer">[lib.streambuf.virt.buffer]</A> 
paragraph 1 is inconsistent with the Effects clause for seekoff. </P>
<P><B>Proposed resolution:</B></P>
<P>Make this paragraph, the Effects clause for setbuf, consistent in wording 
with the Effects clause for seekoff in paragraph 3 by amending paragraph 1 to 
indicate the purpose of setbuf: </P>
<P>Original text:</P>
<BLOCKQUOTE>1 Effects: Performs an operation that is defined separately for 
  each class derived from basic_streambuf in this clause (27.7.1.3, 27.8.1.4). 
</BLOCKQUOTE>
<P>Proposed text:</P>
<BLOCKQUOTE>1 Effects: Influences stream buffering in a way that is defined 
  separately for each class derived from basic_streambuf in this clause 
  (27.7.1.3, 27.8.1.4). </BLOCKQUOTE>
<P><B>Rationale:</B></P>
<P>The LWG doesn't believe there is any normative difference between the 
existing wording and what's in the proposed resolution, but the change may make 
the intent clearer.</P>
<HR>
<A name=365>
<H3>365.&nbsp;Lack of const-qualification in clause 27</H3></A>
<P><B>Section:</B>&nbsp;27 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.input.output">[lib.input.output]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Review">Review</A>&nbsp; 
<B>Submitter:</B>&nbsp;Walter Brown, Marc Paterno&nbsp; <B>Date:</B>&nbsp;10 May 
2002</P>
<P>Some stream and streambuf member functions are declared non-const, even 
thought they appear only to report information rather than to change an object's 
logical state. They should be declared const. See document N1360 for details and 
rationale. </P>
<P>The list of member functions under discussion: <TT>in_avail</TT>, 
<TT>showmanyc</TT>, <TT>tellg</TT>, <TT>tellp</TT>, <TT>is_open</TT>.</P>
<P>Related issue: <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#73">73</A> </P>
<P><B>Proposed resolution:</B></P>
<P>In 27.8.1.5, 27.8.1.7, 27.8.1.8, 27.8.1.10, 27.8.1.11, and 27.8.1.13</P>
<P>Replace</P><PRE>  bool is_open();
</PRE>
<P>with</P><PRE>  bool is_open() const;
</PRE>
<P><B>Rationale:</B></P>
<P>Of the changes proposed in N1360, the only one that is safe is changing the 
filestreams' is_open to const. The LWG believed that this was NAD the first time 
it considered this issue (issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#73">73</A>), but now 
thinks otherwise. The corresponding streambuf member function, after all,is 
already const.</P>
<P>The other proposed changes are less safe, because some streambuf functions 
that appear merely to report a value do actually perform mutating operations. 
It's not even clear that they should be considered "logically const", because 
streambuf has two interfaces, a public one and a protected one. These functions 
may, and often do, change the state as exposed by the protected interface, even 
if the state exposed by the public interface is unchanged.</P>
<P>Note that implementers can make this change in a binary compatible way by 
providing both overloads; this would be a conforming extension.</P>
<HR>
<A name=366>
<H3>366.&nbsp;Excessive const-qualification</H3></A>
<P><B>Section:</B>&nbsp;27 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.input.output">[lib.input.output]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Walter Brown, Marc Paterno&nbsp; <B>Date:</B>&nbsp;10 May 
2002</P>
<P>The following member functions are declared const, yet return non-const 
pointers. We believe they are should be changed, because they allow code that 
may surprise the user. See document N1360 for details and rationale. </P>
<P><I>[Santa Cruz: the real issue is that we've got const member functions that 
return pointers to non-const, and N1360 proposes replacing them by overloaded 
pairs. There isn't a consensus about whether this is a real issue, since we've 
never said what our constness policy is for iostreams. N1360 relies on a 
distinction between physical constness and logical constness; that distinction, 
or those terms, does not appear in the standard.]</I></P>
<P><B>Proposed resolution:</B></P>
<P>In 27.4.4 and 27.4.4.2</P>
<P>Replace</P><PRE>  basic_ostream&lt;charT,traits&gt;* tie() const;
</PRE>
<P>with</P><PRE>  basic_ostream&lt;charT,traits&gt;* tie();
  const basic_ostream&lt;charT,traits&gt;* tie() const;
</PRE>
<P>and replace</P><PRE>  basic_streambuf&lt;charT,traits&gt;* rdbuf() const;
</PRE>
<P>with</P><PRE>  basic_streambuf&lt;charT,traits&gt;* rdbuf();
  const basic_streambuf&lt;charT,traits&gt;* rdbuf() const;
</PRE>
<P>In 27.5.2 and 27.5.2.3.1</P>
<P>Replace</P><PRE>  char_type* eback() const;
</PRE>
<P>with</P><PRE>  char_type* eback();
  const char_type* eback() const;
</PRE>
<P>Replace</P><PRE>  char_type gptr() const;
</PRE>
<P>with</P><PRE>  char_type* gptr();
  const char_type* gptr() const;
</PRE>
<P>Replace</P><PRE>  char_type* egptr() const;
</PRE>
<P>with</P><PRE>  char_type* egptr();
  const char_type* egptr() const;
</PRE>
<P>In 27.5.2 and 27.5.2.3.2</P>
<P>Replace</P><PRE>  char_type* pbase() const;
</PRE>
<P>with</P><PRE>  char_type* pbase();
  const char_type* pbase() const;
</PRE>
<P>Replace</P><PRE>  char_type* pptr() const;
</PRE>
<P>with</P><PRE>  char_type* pptr();
  const char_type* pptr() const;
</PRE>
<P>Replace</P><PRE>  char_type* epptr() const;
</PRE>
<P>with</P><PRE>  char_type* epptr();
  const char_type* epptr() const;
</PRE>
<P>In 27.7.2, 27.7.2.2, 27.7.3 27.7.3.2, 27.7.4, and 27.7.6</P>
<P>Replace</P><PRE>  basic_stringbuf&lt;charT,traits,Allocator&gt;* rdbuf() const;
</PRE>
<P>with</P><PRE>  basic_stringbuf&lt;charT,traits,Allocator&gt;* rdbuf();
  const basic_stringbuf&lt;charT,traits,Allocator&gt;* rdbuf() const;
</PRE>
<P>In 27.8.1.5, 27.8.1.7, 27.8.1.8, 27.8.1.10, 27.8.1.11, and 27.8.1.13</P>
<P>Replace</P><PRE>  basic_filebuf&lt;charT,traits&gt;* rdbuf() const;
</PRE>
<P>with</P><PRE>  basic_filebuf&lt;charT,traits&gt;* rdbuf();
  const basic_filebuf&lt;charT,traits&gt;* rdbuf() const;
</PRE>
<HR>
<A name=368>
<H3>368.&nbsp;basic_string::replace has two "Throws" paragraphs</H3></A>
<P><B>Section:</B>&nbsp;21.3.5.6 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-strings.html#lib.string::replace">[lib.string::replace]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Beman Dawes&nbsp; <B>Date:</B>&nbsp;3 Jun 2002</P>
<P>21.3.5.6 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-strings.html#lib.string::replace">[lib.string::replace]</A> 
basic_string::replace, second signature, given in paragraph 1, has two "Throws" 
paragraphs (3 and 5). </P>
<P>In addition, the second "Throws" paragraph (5) includes specification 
(beginning with "Otherwise, the function replaces ...") that should be part of 
the "Effects" paragraph. </P>
<P><B>Proposed resolution:</B></P>
<P><I>[This is a typo that escalated. It's clear that what's in the Standard is 
wrong. It's less clear what the fix ought to be. Someone who understands string 
replace well needs to work on this.]</I></P>
<HR>
<A name=369>
<H3>369.&nbsp;io stream objects and static ctors</H3></A>
<P><B>Section:</B>&nbsp;27.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.iostream.objects">[lib.iostream.objects]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Ruslan Abdikeev&nbsp; <B>Date:</B>&nbsp;8 Jul 2002</P>
<P>Is it safe to use standard iostream objects from constructors of static 
objects? Are standard iostream objects constructed and are their associations 
established at that time? </P>
<P>Surpisingly enough, Standard does NOT require that.</P>
<P>27.3/2 [lib.iostream.objects] guarantees that standard iostream objects are 
constructed and their associations are established before the body of main() 
begins execution. It also refers to ios_base::Init class as the panacea for 
constructors of static objects. </P>
<P>However, there's nothing in 27.3 [lib.iostream.objects], in 27.4.2 
[lib.ios.base], and in 27.4.2.1.6 [lib.ios::Init], that would require 
implementations to allow access to standard iostream objects from constructors 
of static objects. </P>
<P>Details:</P>
<P>Core text refers to some magic object ios_base::Init, which will be discussed 
below:</P>
<BLOCKQUOTE>"The [standard iostream] objects are constructed, and their 
  associations are established at some time prior to or during first time an 
  object of class basic_ios&lt;charT,traits&gt;::Init is constructed, and in any 
  case before the body of main begins execution." (27.3/2 
  [lib.iostream.objects]) </BLOCKQUOTE>
<P>The first <I>non-normative</I> footnote encourages implementations to 
initialize standard iostream objects earlier than required. </P>
<P>However, the second <I>non-normative</I> footnote makes an explicit and 
unsupported claim:</P>
<BLOCKQUOTE>"Constructors and destructors for static objects can access these 
  [standard iostream] objects to read input from stdin or write output to stdout 
  or stderr." (27.3/2 footnote 265 [lib.iostream.objects]) </BLOCKQUOTE>
<P>The only bit of magic is related to that ios_base::Init class. AFAIK, the 
rationale behind ios_base::Init was to bring an instance of this class to each 
translation unit which #included &lt;iostream&gt; or related header. Such an 
inclusion would support the claim of footnote quoted above, because in order to 
use some standard iostream object it is necessary to #include &lt;iostream&gt;. 
</P>
<P>However, while Standard explicitly describes ios_base::Init as an appropriate 
class for doing the trick, I failed to found a mention of an _instance_ of 
ios_base::Init in Standard. </P>
<P><B>Proposed resolution:</B></P>
<P>At the end of header &lt;iostream&gt; synopsis in 27.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.iostream.objects">[lib.iostream.objects]</A> 
</P><PRE>       namespace std
       {
          ... extern istream cin; ...
</PRE>
<P>add the following lines</P><PRE>          namespace
          {
             ios_base::Init &lt;some_implementation_defined_name&gt;;
          }
        }
</PRE>
<P><I>[Santa Cruz: The LWG is leaning toward NAD. There isn't any normative 
wording saying that the Init scheme will be used, but that is probably 
intentional. Implementers use dirty tricks for iostream initialization, and 
doing it portably is somewhere between difficult and impossible. Too much 
constraint in this area is dangerous, and if we are to make any changes it would 
probably be more appropriate forthem to be nonnormative. Martin will try to come 
up with clearer wording that expreses this intent.]</I></P>
<HR>
<A name=370>
<H3>370.&nbsp;Minor error in basic_istream::get</H3></A>
<P><B>Section:</B>&nbsp;27.6.1.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.istream.unformatted">[lib.istream.unformatted]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A>&nbsp; 
<B>Submitter:</B>&nbsp;Ray Lischner&nbsp; <B>Date:</B>&nbsp;15 Jul 2002</P>
<P>Defect report for description of basic_istream::get (section 27.6.1.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.istream.unformatted">[lib.istream.unformatted]</A>), 
paragraph 15. The description for the get function with the following 
signature:</P><PRE>  basic_istream&lt;charT,traits&gt;&amp; get(basic_streambuf&lt;char_type,traits&gt;&amp;
  sb);
</PRE>
<P>is incorrect. It reads</P>
<BLOCKQUOTE>Effects: Calls get(s,n,widen('\n')) </BLOCKQUOTE>
<P>which I believe should be:</P>
<BLOCKQUOTE>Effects: Calls get(sb,widen('\n')) </BLOCKQUOTE>
<P><B>Proposed resolution:</B></P>
<P>Change the <B>Effects</B> paragraph to:</P>
<BLOCKQUOTE>Effects: Calls get(sb,this-&gt;widen('\n')) </BLOCKQUOTE>
<P><I>[Pre-Oxford: Minor correction from Howard: replaced 'widen' with 
'this-&gt;widen'.]</I></P>
<P><B>Rationale:</B></P>
<P>Fixes an obvious typo.</P>
<HR>
<A name=371>
<H3>371.&nbsp;Stability of multiset and multimap member functions</H3></A>
<P><B>Section:</B>&nbsp;23.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-containers.html#lib.container.requirements">[lib.container.requirements]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Frank Compagner&nbsp; <B>Date:</B>&nbsp;20 Jul 2002</P>
<P>The requirements for multiset and multimap containers (23.1 
[lib.containers.requirements], 23.1.2 [lib.associative.reqmnts], 23.3.2 
[lib.multimap] and 23.3.4 [lib.multiset]) make no mention of the stability of 
the required (mutating) member functions. It appears the standard allows these 
functions to reorder equivalent elements of the container at will, yet the 
pervasive red-black tree implementation appears to provide stable behaviour. 
</P>
<P>This is of most concern when considering the behaviour of erase(). A 
stability requirement would guarantee the correct working of the following 
'idiom' that removes elements based on a certain predicate function. </P><PRE>  multimap&lt;int, int&gt; m;
  multimap&lt;int, int&gt;::iterator i = m.begin();
  while (i != m.end()) {
      if (pred(i))
          m.erase (i++);
      else
          ++i;
  }
</PRE>
<P>Although clause 23.1.2/8 guarantees that i remains a valid iterator througout 
this loop, absence of the stability requirement could potentially result in 
elements being skipped. This would make this code incorrect, and, furthermore, 
means that there is no way of erasing these elements without iterating first 
over the entire container, and second over the elements to be erased. This would 
be unfortunate, and have a negative impact on both performance and code 
simplicity. </P>
<P>If the stability requirement is intended, it should be made explicit 
(probably through an extra paragraph in clause 23.1.2). </P>
<P>If it turns out stability cannot be guaranteed, i'd argue that a remark or 
footnote is called for (also somewhere in clause 23.1.2) to warn against relying 
on stable behaviour (as demonstrated by the code above). If most implementations 
will display stable behaviour, any problems emerging on an implementation 
without stable behaviour will be hard to track down by users. This would also 
make the need for an erase_if() member function that much greater. </P>
<P>This issue is somewhat related to LWG issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#130">130</A>.</P>
<P><I>[Santa Cruz: More people need to look at this. Much user code may assume 
stability. On the other hand, it seems drastic to add a new requirement 
now.]</I></P>
<P><B>Proposed resolution:</B></P>
<HR>
<A name=373>
<H3>373.&nbsp;Are basic_istream and basic_ostream to use 
(exceptions()&amp;badbit) != 0 ?</H3></A>
<P><B>Section:</B>&nbsp;27.6.1.2.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.istream.formatted.reqmts">[lib.istream.formatted.reqmts]</A>, 
27.6.2.5.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.ostream.formatted.reqmts">[lib.ostream.formatted.reqmts]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A>&nbsp; 
<B>Submitter:</B>&nbsp;Keith Baker&nbsp; <B>Date:</B>&nbsp;23 Jul 2002</P>
<P>In 27.6.1.2.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.istream.formatted.reqmts">[lib.istream.formatted.reqmts]</A> 
and 27.6.2.5.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.ostream.formatted.reqmts">[lib.ostream.formatted.reqmts]</A> 
(exception()&amp;badbit) != 0 is used in testing for rethrow, yet exception() is 
the constructor to class std::exception in 18.6.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-support.html#lib.exception">[lib.exception]</A> 
that has no return type. Should member function exceptions() found in 27.4.4 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.ios">[lib.ios]</A> 
be used instead? </P>
<P><B>Proposed resolution:</B></P>
<P>In 27.6.1.2.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.istream.formatted.reqmts">[lib.istream.formatted.reqmts]</A> 
and 27.6.2.5.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.ostream.formatted.reqmts">[lib.ostream.formatted.reqmts]</A>, 
change "(exception()&amp;badbit) != 0" to "(exceptions()&amp;badbit) != 0". </P>
<P><B>Rationale:</B></P>
<P>Fixes an obvious typo.</P>
<HR>
<A name=375>
<H3>375.&nbsp;basic_ios should be ios_base in 27.7.1.3</H3></A>
<P><B>Section:</B>&nbsp;27.7.1.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.stringbuf.virtuals">[lib.stringbuf.virtuals]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A>&nbsp; 
<B>Submitter:</B>&nbsp;Ray Lischner&nbsp; <B>Date:</B>&nbsp;14 Aug 2002</P>
<P>In Section 27.7.1.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.stringbuf.virtuals">[lib.stringbuf.virtuals]</A>: 
Table 90, Table 91, and paragraph 14 all contain references to "basic_ios::" 
which should be "ios_base::". </P>
<P><B>Proposed resolution:</B></P>
<P>Change all references to "basic_ios" in Table 90, Table 91, and paragraph 14 
to "ios_base". </P>
<P><B>Rationale:</B></P>
<P>Fixes an obvious typo.</P>
<HR>
<A name=376>
<H3>376.&nbsp;basic_streambuf semantics</H3></A>
<P><B>Section:</B>&nbsp;27.7.1.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.stringbuf.virtuals">[lib.stringbuf.virtuals]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Ray Lischner&nbsp; <B>Date:</B>&nbsp;14 Aug 2002</P>
<P>In Section 27.7.1.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.stringbuf.virtuals">[lib.stringbuf.virtuals]</A>, 
Table 90, the implication is that the four conditions should be mutually 
exclusive, but they are not. The first two cases, as written, are subcases of 
the third. I think it would be clearer if the conditions were rewritten as 
follows: </P>
<BLOCKQUOTE>
  <P>(which &amp; (ios_base::in|ios_base::out)) == ios_base::in </P>
  <P>(which &amp; (ios_base::in|ios_base::out)) == ios_base::out </P>
  <P>(which &amp; (ios_base::in|ios_base::out)) == (ios_base::in|ios_base::out) 
  and way == either ios_base::beg or ios_base::end </P>
  <P>Otherwise</P></BLOCKQUOTE>
<P>As written, it is unclear what should be the result if cases 1 &amp; 2 are 
true, but case 3 is false, e.g., </P>
<BLOCKQUOTE>seekoff(0, ios_base::cur, ios_base::in | ios_base::out) 
</BLOCKQUOTE>
<P><I>[Santa Cruz: The ambiguity seems real. We need to do a survey of 
implementations before we decide on a solution.]</I></P>
<P><B>Proposed resolution:</B></P>
<HR>
<A name=378>
<H3>378.&nbsp;locale immutability and locale::operator=()</H3></A>
<P><B>Section:</B>&nbsp;22.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.locale">[lib.locale]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Martin Sebor&nbsp; <B>Date:</B>&nbsp;6 Sep 2002</P>
<P>I think there is a problem with 22.1.1, p6 which says that </P><PRE>    -6- An instance of locale is immutable; once a facet reference
        is obtained from it, that reference remains usable as long
        as the locale value itself exists.
</PRE>
<P>and 22.1.1.2, p4: </P><PRE>    const locale&amp; operator=(const locale&amp; other) throw();

    -4- Effects: Creates a copy of other, replacing the current value.
</PRE>
<P>How can a reference to a facet obtained from a locale object remain valid 
after an assignment that clearly must replace all the facets in the locale 
object? Imagine a program such as this </P><PRE>    std::locale loc ("de_DE");
    const std::ctype&lt;char&gt; &amp;r0 = std::use_facet&lt;std::ctype&lt;char&gt; &gt;(loc);
    loc = std::locale ("en_US");
    const std::ctype&lt;char&gt; &amp;r1 = std::use_facet&lt;std::ctype&lt;char&gt; &gt;(loc);
</PRE>
<P>Is r0 really supposed to be preserved and destroyed only when loc goes out of 
scope? </P>
<P><B>Proposed resolution:</B></P>
<P>Suggest to replace 22.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.locale">[lib.locale]</A>, 
p6 with </P><PRE>    -6- Unless assigned a new value, locale objects are immutable;
        once a facet reference is obtained from it, that reference
        remains usable as long as the locale object itself exists
        or until the locale object is assigned the value of another,
        distinct locale object.
</PRE>
<P><I>[Santa Cruz: Dietmar agrees with this general direction, but is 
uncomfortable about the proposed wording. He and Martin will try to come up with 
better wording.]</I></P>
<HR>
<A name=379>
<H3>379.&nbsp;nonsensical ctype::do_widen() requirement</H3></A>
<P><B>Section:</B>&nbsp;22.2.1.1.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.locale.ctype.virtuals">[lib.locale.ctype.virtuals]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Review">Review</A>&nbsp; 
<B>Submitter:</B>&nbsp;Martin Sebor&nbsp; <B>Date:</B>&nbsp;6 Sep 2002</P>
<P>The last sentence in 22.2.1.1.2, p11 below doesn't seem to make sense. </P><PRE>  charT do_widen (char c) const;

  -11- Effects: Applies the simplest reasonable transformation from
       a char value or sequence of char values to the corresponding
       charT value or values. The only characters for which unique
       transformations are required are those in the basic source
       character set (2.2). For any named ctype category with a
       ctype&lt;charT&gt; facet ctw and valid ctype_base::mask value
       M (is(M, c) || !ctw.is(M, do_widen(c))) is true.
</PRE>
<P>Shouldn't the last sentence instead read </P><PRE>       For any named ctype category with a ctype&lt;char&gt; facet ctc
       and valid ctype_base::mask value M
       (ctc.is(M, c) || !is(M, do_widen(c))) is true.
</PRE>
<P>I.e., if the narrow character c is not a member of a class of characters then 
neither is the widened form of c. (To paraphrase footnote 224.) </P>
<P><B>Proposed resolution:</B></P>
<P>Replace the last sentence of 22.2.1.1.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.locale.ctype.virtuals">[lib.locale.ctype.virtuals]</A>, 
p11 with the following text: </P><PRE>       For any named ctype category with a ctype&lt;char&gt; facet ctc
       and valid ctype_base::mask value M
       (ctc.is(M, c) || !is(M, do_widen(c))) is true.
</PRE>
<P><B>Rationale:</B></P>
<P>The LWG believes this is just a typo, and that this is the correct fix.</P>
<HR>
<A name=380>
<H3>380.&nbsp;typos in codecvt tables 53 and 54</H3></A>
<P><B>Section:</B>&nbsp;22.2.1.5.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.locale.codecvt.virtuals">[lib.locale.codecvt.virtuals]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A>&nbsp; 
<B>Submitter:</B>&nbsp;Martin Sebor&nbsp; <B>Date:</B>&nbsp;6 Sep 2002</P>
<P>Tables 53 and 54 in 22.2.1.5.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.locale.codecvt.virtuals">[lib.locale.codecvt.virtuals]</A> 
are both titled "convert result values," when surely "do_in/do_out result 
values" must have been intended for Table 53 and "do_unshift result values" for 
Table 54. </P>
<P>Table 54, row 3 says that the meaning of partial is "more characters needed 
to be supplied to complete termination." The function is not supplied any 
characters, it is given a buffer which it fills with characters or, more 
precisely, destination elements (i.e., an escape sequence). So partial means 
that space for more than (to_limit - to) destination elements was needed to 
terminate a sequence given the value of state. </P>
<P><B>Proposed resolution:</B></P>
<P>Change the title of Table 53 to "do_in/do_out result values" and the title of 
Table 54 to "do_unshift result values." </P>
<P>Change the text in Table 54, row 3 (the <B>partial</B> row), under the 
heading Meaning, to "space for more than (to_limit - to) destination elements 
was needed to terminate a sequence given the value of state." </P>
<HR>
<A name=381>
<H3>381.&nbsp;detection of invalid mbstate_t in codecvt</H3></A>
<P><B>Section:</B>&nbsp;22.2.1.5.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.locale.codecvt.virtuals">[lib.locale.codecvt.virtuals]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A>&nbsp; 
<B>Submitter:</B>&nbsp;Martin Sebor&nbsp; <B>Date:</B>&nbsp;6 Sep 2002</P>
<P>All but one codecvt member functions that take a state_type argument list as 
one of their preconditions that the state_type argument have a valid value. 
However, according to 22.2.1.5.2, p6, codecvt::do_unshift() is the only codecvt 
member that is supposed to return error if the state_type object is invalid. 
</P>
<P>It seems to me that the treatment of state_type by all codecvt member 
functions should be the same and the current requirements should be changed. 
Since the detection of invalid state_type values may be difficult in general or 
computationally expensive in some specific cases, I propose the following: </P>
<P><B>Proposed resolution:</B></P>
<P>Add a new paragraph before 22.2.1.5.2, p5, and after the function declaration 
below </P><PRE>    result do_unshift(stateT&amp; state,
    externT* to, externT* to_limit, externT*&amp; to_next) const;
</PRE>
<P>as follows: </P><PRE>    Requires: (to &lt;= to_end) well defined and true; state initialized,
    if at the beginning of a sequence, or else equal to the result of
    converting the preceding characters in the sequence.
</PRE>
<P>and change the text in Table 54, row 4, the <B>error</B> row, under the 
heading Meaning, from </P><PRE>    state has invalid value
</PRE>
<P>to </P><PRE>    an unspecified error has occurred
</PRE>
<P><B>Rationale:</B></P>
<P>The intent is that implementations should not be required to detect invalid 
state values; such a requirement appears nowhere else. An invalid state value is 
a precondition violation, <I>i.e.</I> undefined behavior. Implementations that 
do choose to detect invalid state values, or that choose to detect any other 
kind of error, may return <B>error</B> as an indication.</P>
<HR>
<A name=382>
<H3>382.&nbsp;codecvt do_in/out result</H3></A>
<P><B>Section:</B>&nbsp;22.2.1.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.locale.codecvt">[lib.locale.codecvt]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Review">Review</A>&nbsp; 
<B>Submitter:</B>&nbsp;Martin Sebor&nbsp; <B>Date:</B>&nbsp;30 Aug 2002</P>
<P>It seems that the descriptions of codecvt do_in() and do_out() leave 
sufficient room for interpretation so that two implementations of codecvt may 
not work correctly with the same filebuf. Specifically, the following seems less 
than adequately specified: </P>
<OL>
  <LI>the conditions under which the functions terminate 
  <LI>precisely when the functions return ok 
  <LI>precisely when the functions return partial 
  <LI>the full set of conditions when the functions return error </LI></OL>
<OL>
  <LI>22.2.1.5.2 <A 
  href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.locale.codecvt.virtuals">[lib.locale.codecvt.virtuals]</A>, 
  p2 says this about the effects of the function: ...Stops if it encounters a 
  character it cannot convert... This assumes that there *is* a character to 
  convert. What happens when there is a sequence that doesn't form a valid 
  source character, such as an unassigned or invalid UNICODE character, or a 
  sequence that cannot possibly form a character (e.g., the sequence "\xc0\xff" 
  in UTF-8)? 
  <LI>Table 53 says that the function returns codecvt_base::ok to indicate that 
  the function(s) "completed the conversion." Suppose that the source sequence 
  is "\xc0\x80" in UTF-8, with from pointing to '\xc0' and (from_end==from + 1). 
  It is not clear whether the return value should be ok or partial (see below). 
  <LI>Table 53 says that the function returns codecvt_base::partial if "not all 
  source characters converted." With the from pointers set up the same way as 
  above, it is not clear whether the return value should be partial or ok (see 
  above). 
  <LI>Table 53, in the row describing the meaning of error mistakenly refers to 
  a "from_type" character, without the symbol from_type having been defined. 
  Most likely, the word "source" character is intended, although that is not 
  sufficient. The functions may also fail when they encounter an invalid source 
  sequence that cannot possibly form a valid source character (e.g., as 
  explained in bullet 1 above). </LI></OL>
<P>Finally, the conditions described at the end of 22.2.1.5.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.locale.codecvt.virtuals">[lib.locale.codecvt.virtuals]</A>, 
p4 don't seem to be possible: </P>
<BLOCKQUOTE>"A return value of partial, if (from_next == from_end), indicates 
  that either the destination sequence has not absorbed all the available 
  destination elements, or that additional source elements are needed before 
  another destination element can be produced." </BLOCKQUOTE>
<P>If the value is partial, it's not clear to me that (from_next ==from_end) 
could ever hold if there isn't enough room in the destination buffer. In order 
for (from_next==from_end) to hold, all characters in that range must have been 
successfully converted (according to 22.2.1.5.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.locale.codecvt.virtuals">[lib.locale.codecvt.virtuals]</A>, 
p2) and since there are no further source characters to convert, no more room in 
the destination buffer can be needed. </P>
<P>It's also not clear to me that (from_next==from_end) could ever hold if 
additional source elements are needed to produce another destination character 
(not element as incorrectly stated in the text). partial is returned if "not all 
source characters have been converted" according to Table 53, which also implies 
that (from_next==from) does NOT hold. </P>
<P>Could it be that the intended qualifying condition was actually (from_next != 
from_end), i.e., that the sentence was supposed to read </P>
<BLOCKQUOTE>"A return value of partial, if (from_next != from_end),..." 
</BLOCKQUOTE>
<P>which would make perfect sense, since, as far as I understand it, partial can 
only occur if (from_next != from_end)? </P>
<P><B>Proposed resolution:</B></P>
<P>To address these issues, I propose that paragraphs 2, 3, and 4 be rewritten 
as follows. The proposal incorporates the accepted resolution of lwg issue 19. 
</P><PRE>-2- Effects: Converts characters in the range of source elements
    [from, from_end), placing the results in sequential positions
    starting at destination to. Converts no more than (from_end &shy; from)
    source elements, and stores no more than (to_limit &shy; to)
    destination elements.

    Stops if it encounters a sequence of source elements it cannot
    convert to a valid destination character. It always leaves the
    from_next and to_next pointers pointing one beyond the last
    element successfully converted.

    [Note: If returns noconv, internT and externT are the same type
    and the converted sequence is identical to the input sequence
    [from, from_next). to_next is set equal to to, the value of
    state is unchanged, and there are no changes to the values in
    [to, to_limit). --end note]

-3- Notes: Its operations on state are unspecified.
    [Note: This argument can be used, for example, to maintain shift
    state, to specify conversion options (such as count only), or to
    identify a cache of seek offsets. --end note]

-4- Returns: An enumeration value, as summarized in Table 53:

    Table 53 -- do_in/do_out result values

     Value      Meaning
    +---------+----------------------------------------------------+
    | ok      | successfully completed the conversion of all       |
    |         | complete characters in the source range            |
    +---------+----------------------------------------------------+
    | partial | the characters in the source range would, after    |
    |         | conversion, require space greater than that        |
    |         | available in the destination range                 |
    +---------+----------------------------------------------------+
    | error   | encountered either a sequence of elements in the   |
    |         | source range forming a valid source character that |
    |         | could not be converted to a destination character, |
    |         | or a sequence of elements in the source range that |
    |         | could not possibly form a valid source character   |
    +---------+----------------------------------------------------+
    | noconv  | internT and externT are the same type, and input   |
    |         | sequence is identical to converted sequence        |
    +---------+----------------------------------------------------+

    A return value of partial, i.e., if (from_next != from_end),
    indicates that either the destination sequence has not absorbed
    all the available destination elements, or that additional
    source elements are needed before another destination character
    can be produced.
</PRE>
<P><I>[Santa Cruz: The LWG agrees that this is an important issue and that this 
general direction is probably correct. Dietmar, Howard, PJP, and Matt will 
review this wording.]</I></P>
<HR>
<A name=383>
<H3>383.&nbsp;Bidirectional iterator assertion typo</H3></A>
<P><B>Section:</B>&nbsp;24.1.4 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.bidirectional.iterators">[lib.bidirectional.iterators]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Ready">Ready</A>&nbsp; 
<B>Submitter:</B>&nbsp;ysapir (submitted via comp.std.c++)&nbsp; 
<B>Date:</B>&nbsp;17 Oct 2002</P>
<P>Following a discussion on the boost list regarding end iterators and the 
possibility of performing operator--() on them, it seems to me that there is a 
typo in the standard. This typo has nothing to do with that discussion. </P>
<P>I have checked this newsgroup, as well as attempted a search of the 
Active/Defect/Closed Issues List on the site for the words "s is derefer" so I 
believe this has not been proposed before. Furthermore, the "Lists by Index" 
mentions only DR <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#299">299</A> on section 
24.1.4, and DR <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#299">299</A> is not 
related to this issue. </P>
<P>The standard makes the following assertion on bidirectional iterators, in 
section 24.1.4 [lib.bidirectional.iterators], Table 75: </P><PRE>                         operational  assertion/note
expression  return type   semantics    pre/post-condition

--r          X&amp;                        pre: there exists s such
                                       that r == ++s.
                                       post: s is dereferenceable.
                                       --(++r) == r.
                                       --r == --s implies r == s.
                                       &amp;r == &amp;--r.
</PRE>
<P>(See <A 
href="http://aspn.activestate.com/ASPN/Mail/Message/boost/1395763">http://aspn.activestate.com/ASPN/Mail/Message/boost/1395763</A>.) 
</P>
<P>In particular, "s is dereferenceable" seems to be in error. It seems that the 
intention was to say "r is dereferenceable". </P>
<P>If it were to say "r is dereferenceable" it would make perfect sense. Since s 
must be dereferenceable prior to operator++, then the natural result of 
operator-- (to undo operator++) would be to make r dereferenceable. Furthermore, 
without other assertions, and basing only on precondition and postconditions, we 
could not otherwise know this. So it is also interesting information. </P>
<P><B>Proposed resolution:</B></P>
<P>Change the guarantee to "postcondition: r is dereferenceable." </P>
<P><B>Rationale:</B></P>
<P>Fixes an obvious typo</P>
<HR>
<A name=384>
<H3>384.&nbsp;equal_range has unimplementable runtime complexity</H3></A>
<P><B>Section:</B>&nbsp;25.3.3.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-algorithms.html#lib.equal.range">[lib.equal.range]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Open">Open</A>&nbsp; 
<B>Submitter:</B>&nbsp;Hans Bos&nbsp; <B>Date:</B>&nbsp;18 Oct 2002</P>
<P>Section 25.3.3.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-algorithms.html#lib.equal.range">[lib.equal.range]</A> 
states that at most 2 * log(last - first) + 1 comparisons are allowed for 
equal_range. </P>
<P>It is not possible to implement equal_range with these constraints.</P>
<P>In a range of one element as in:</P><PRE>    int x = 1;
    equal_range(&amp;x, &amp;x + 1, 1)
</PRE>
<P>it is easy to see that at least 2 comparison operations are needed.</P>
<P>For this case at most 2 * log(1) + 1 = 1 comparison is allowed.</P>
<P>I have checked a few libraries and they all use the same (nonconforming) 
algorithm for equal_range that has a complexity of</P><PRE>     2* log(distance(first, last)) + 2.
</PRE>
<P>I guess this is the algorithm that the standard assumes for equal_range.</P>
<P>It is easy to see that 2 * log(distance) + 2 comparisons are enough since 
equal range can be implemented with lower_bound and upper_bound (both 
log(distance) + 1). </P>
<P>I think it is better to require something like 2log(distance) + O(1) (or even 
logarithmic as multiset::equal_range). Then an implementation has more room to 
optimize for certain cases (e.g. have log(distance) characteristics when at most 
match is found in the range but 2log(distance) + 4 for the worst case). </P>
<P><I>[Santa Cruz: The issue is real, but of greater scope than just 
equal_range: it affects all of the binary search algorithms. What is the 
complexity supposed to be for ranges of 0 or 1 elements? What base are we using 
for the logarithm? Are these bounds supposed to be exact, or asymptotic? (If the 
latter, of course, then none of the other questions matter.)]</I></P>
<P><B>Proposed resolution:</B></P>
<HR>
<A name=385>
<H3>385.&nbsp;Does call by value imply the CopyConstructible 
requirement?</H3></A>
<P><B>Section:</B>&nbsp;17 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-intro.html#lib.library">[lib.library]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#New">New</A>&nbsp; 
<B>Submitter:</B>&nbsp;Matt Austern&nbsp; <B>Date:</B>&nbsp;23 Oct 2002</P>
<P>Many function templates have parameters that are passed by value; a typical 
example is <TT>find_if</TT>'s <I>pred</I> parameter in 25.1.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-algorithms.html#lib.alg.find">[lib.alg.find]</A>. 
Are the corresponding template parameters (<TT>Predicate</TT> in this case) 
implicitly required to be CopyConstructible, or does that need to be spelled out 
explicitly? </P>
<P>This isn't quite as silly a question as it might seem to be at first sight. 
If you call <TT>find_if</TT> in such a way that template argument deduction 
applies, then of course you'll get call by value and you need to provide a copy 
constructor. If you explicitly provide the template arguments, however, you can 
force call by reference by writing something like <TT>find_if&lt;my_iterator, 
my_predicate&amp;&gt;</TT>. The question is whether implementation are required 
to accept this, or whether this is ill-formed because my_predicate&amp; is not 
CopyConstructible. </P>
<P>The scope of this problem, if it is a problem, is unknown. Function object 
arguments to generic algorithms in clauses 25 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-algorithms.html#lib.algorithms">[lib.algorithms]</A> 
and 26 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.numerics">[lib.numerics]</A> 
are obvious examples. A review of the whole library is necessary. </P>
<P><B>Proposed resolution:</B></P>
<HR>
<A name=386>
<H3>386.&nbsp;Reverse iterator's operator[] has impossible return type</H3></A>
<P><B>Section:</B>&nbsp;24.4.1.3.11 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.reverse.iter.opindex">[lib.reverse.iter.opindex]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#New">New</A>&nbsp; 
<B>Submitter:</B>&nbsp;Matt Austern&nbsp; <B>Date:</B>&nbsp;23 Oct 2002</P>
<P>In 24.4.1.3.11 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.reverse.iter.opindex">[lib.reverse.iter.opindex]</A>, 
<TT>reverse_iterator&lt;&gt;::operator[]</TT> is specified as having a return 
type of <TT>reverse_iterator::reference</TT>, which is the same as 
<TT>iterator_traits&lt;Iterator&gt;::reference</TT>. (Where <TT>Iterator</TT> is 
the underlying iterator type.)</P>
<P>The trouble is that <TT>Iterator</TT>'s own operator[] doesn't necessarily 
have a return type of <TT>iterator_traits&lt;Iterator&gt;::reference</TT>. Its 
return type is merely required to be convertible to <TT>Iterator</TT>'s value 
type. The return type specified for reverse_iterator's operator[] would thus 
appear to be impossible.</P>
<P>Related issue: <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#299">299</A>.</P>
<P><B>Proposed resolution:</B></P>
<HR>
<A name=387>
<H3>387.&nbsp;std::complex over-encapsulated</H3></A>
<P><B>Section:</B>&nbsp;26.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.complex.numbers">[lib.complex.numbers]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Review">Review</A>&nbsp; 
<B>Submitter:</B>&nbsp;Gabriel Dos Reis&nbsp; <B>Date:</B>&nbsp;8 Nov 2002</P>
<P>The absence of explicit description of std::complex&lt;T&gt; layout makes it 
imposible to reuse existing software developed in traditional languages like 
Fortran or C with unambigous and commonly accepted layout assumptions. There 
ought to be a way for practitioners to predict with confidence the layout of 
std::complex&lt;T&gt; whenever T is a numerical datatype. The absence of ways to 
access individual parts of a std::complex&lt;T&gt; object as lvalues unduly 
promotes severe pessimizations. For example, the only way to change, 
independently, the real and imaginary parts is to write something like </P><PRE>complex&lt;T&gt; z;
// ...
// set the real part to r
z = complex&lt;T&gt;(r, z.imag());
// ...
// set the imaginary part to i
z = complex&lt;T&gt;(z.real(), i);
</PRE>
<P>At this point, it seems appropriate to recall that a complex number is, in 
effect, just a pair of numbers with no particular invariant to maintain. 
Existing practice in numerical computations has it that a complex number 
datatype is usually represented by Cartesian coordinates. Therefore the 
over-encapsulation put in the specification of std::complex&lt;&gt; is not 
justified. </P>
<P><B>Proposed resolution:</B></P>
<P>Add the following requirements to 26.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.complex.numbers">[lib.complex.numbers]</A> 
as 26.2/4:</P>
<BLOCKQUOTE>
  <P>If z is an lvalue expression of type cv std::complex&lt;T&gt; then</P>
  <UL>
    <LI>the expression reinterpret_cast&lt;cv T(&amp;)[2]&gt;(z) is well-formed; 
    and 
    <LI>reinterpret_cast&lt;cvT(&amp;)[2]&gt;(z)[0]designates the real part of 
    z; and 
    <LI>reinterpret_cast&lt;cvT(&amp;)[2]&gt;(z)[1]designates the imaginary part 
    of z. </LI></UL>
  <P>Moreover, if a is an expression of pointer type cv complex&lt;T&gt;* and 
  the expression a[i] is well-defined for an integer expression i then: </P>
  <UL>
    <LI>reinterpret_cast&lt;cvT*&gt;(a)[2+i] designates the real part of a[i]; 
    and 
    <LI>reinterpret_cast&lt;cv T*&gt;(a)[2+i+1] designates the imaginary part of 
    a[i]. </LI></UL></BLOCKQUOTE>
<P>In the header synopsis in 26.2.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.complex.synopsis">[lib.complex.synopsis]</A>, 
replace</P><PRE>  template&lt;class T&gt; T real(const complex&lt;T&gt;&amp;);
  template&lt;class T&gt; T imag(const complex&lt;T&gt;&amp;);
</PRE>
<P>with</P><PRE>  template&lt;class T&gt; const T&amp; real(const complex&lt;T&gt;&amp;);
  template&lt;class T&gt;       T&amp; real(      complex&lt;T&gt;&amp;);
  template&lt;class T&gt; const T&amp; imag(const complex&lt;T&gt;&amp;);
  template&lt;class T&gt;       T&amp; imag(      complex&lt;T&gt;&amp;);
</PRE>
<P>In 26.2.7 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.complex.value.ops">[lib.complex.value.ops]</A> 
paragraph 1, change</P><PRE>  template&lt;class T&gt; T real(const complex&lt;T&gt;&amp;);
</PRE>
<P>to</P><PRE>  template&lt;class T&gt; const T&amp; real(const complex&lt;T&gt;&amp;);
  template&lt;class T&gt;       T&amp; real(      complex&lt;T&gt;&amp;);
</PRE>
<P>and change the <B>Returns</B> clause to "<B>Returns:</B> The real part of 
<I>x</I> </P>. 
<P>In 26.2.7 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.complex.value.ops">[lib.complex.value.ops]</A> 
paragraph 2, change</P><PRE>  template&lt;class T&gt; T imag(const complex&lt;T&gt;&amp;);
</PRE>
<P>to</P><PRE>  template&lt;class T&gt; const T&amp; imag(const complex&lt;T&gt;&amp;);
  template&lt;class T&gt;       T&amp; imag(      complex&lt;T&gt;&amp;);
</PRE>
<P>and change the <B>Returns</B> clause to "<B>Returns:</B> The imaginary part 
of <I>x</I> </P>. 
<P><B>Rationale:</B></P>
<P>The LWG believes that C99 compatibility would be enough justification for 
this change even without other considerations. All existing implementations 
already have the layout proposed here.</P>
<HR>
<A name=389>
<H3>389.&nbsp;Const overload of valarray::operator[] returns by value</H3></A>
<P><B>Section:</B>&nbsp;26.3.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.template.valarray">[lib.template.valarray]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#Review">Review</A>&nbsp; 
<B>Submitter:</B>&nbsp;Gabriel Dos Reis&nbsp; <B>Date:</B>&nbsp;8 Nov 2002</P>
<P>Consider the following program:</P><PRE>    #include &lt;iostream&gt;
    #include &lt;ostream&gt;
    #include &lt;vector&gt;
    #include &lt;valarray&gt;
    #include &lt;algorithm&gt;
    #include &lt;iterator&gt;
    template&lt;typename Array&gt;
    void print(const Array&amp; a)
    {
    using namespace std;
    typedef typename Array::value_type T;
    copy(&amp;a[0], &amp;a[0] + a.size(),
    ostream_iterator&lt;T&gt;(std::cout, " "));
    }
    template&lt;typename T, unsigned N&gt;
    unsigned size(T(&amp;)[N]) { return N; }
    int main()
    {
    double array[] = { 0.89, 9.3, 7, 6.23 };
    std::vector&lt;double&gt; v(array, array + size(array));
    std::valarray&lt;double&gt; w(array, size(array));
    print(v); // #1
    std::cout &lt;&lt; std::endl;
    print(w); // #2
    std::cout &lt;&lt; std::endl;
    }
</PRE>
<P>While the call numbered #1 succeeds, the call numbered #2 fails because the 
const version of the member function valarray&lt;T&gt;::operator[](size_t) 
returns a value instead of a const-reference. That seems to be so for no 
apparent reason, no benefit. Not only does that defeats users' expectation but 
it also does hinder existing software (written either in C or Fortran) 
integration within programs written in C++. There is no reason why subscripting 
an expression of type valarray&lt;T&gt; that is const-qualified should not 
return a const T&amp;.</P>
<P><B>Proposed resolution:</B></P>
<P>In the class synopsis in 26.3.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.template.valarray">[lib.template.valarray]</A>, 
and in 26.3.2.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.valarray.access">[lib.valarray.access]</A> 
just above paragraph 1, change</P><PRE>  T operator[](size_t const;)
</PRE>
<P>to</P><PRE>  const T&amp; operator[](size_t const;)
</PRE>
<P><B>Rationale:</B></P>
<P>Return by value seems to serve no purpose. Valaray was explicitly designed to 
have a specified layout so that it could easily be integrated with libraries in 
other languages, and return by value defeats that purpose. It is believed that 
this change will have no impact on allowable optimizations.</P>
<HR>
<A name=390>
<H3>390.&nbsp;CopyConstructible requirements too strict</H3></A>
<P><B>Section:</B>&nbsp;20.1.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-utilities.html#lib.copyconstructible">[lib.copyconstructible]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#New">New</A>&nbsp; 
<B>Submitter:</B>&nbsp;Doug Gregor&nbsp; <B>Date:</B>&nbsp;24 Oct 2002</P>
<P>The CopyConstructible requirements in Table 30 state that for an object t of 
type T (where T is CopyConstructible), the expression &amp;t returns the address 
of t (with type T*). This requirement is overly strict, in that it disallows 
types that overload operator&amp; to not return a value of type T*. This occurs, 
for instance, in the <A href="http://www.boost.org/libs/lambda">Boost.Lambda</A> 
library, where operator&amp; is overloaded for a Boost.Lambda function object to 
return another function object. </P>
<P>Example:</P><PRE>  std::vector&lt;int&gt; u, v;
  int x;
  // ...
  std::transform(u.begin(), u.end(), std::back_inserter(v), _1 * x);
</PRE>
<P>_1 * x returns an unnamed function object with operator&amp; overloaded to 
not return T* , therefore rendering the std::transform call ill-formed. However, 
most standard library implementations will compile this code properly, and the 
viability of such binder libraries is severely hindered by the unnecessary 
restriction in the CopyConstructible requirements. </P>
<P>For reference, the address of an object can be retrieved without using the 
address-of operator with the following function template: </P><PRE>  template &lt;typename T&gt; T* addressof(T&amp; v)
  {
    return reinterpret_cast&lt;T*&gt;(
         &amp;const_cast&lt;char&amp;&gt;(reinterpret_cast&lt;const volatile char &amp;&gt;(v)));
  }
</PRE>
<P>Note: this relates directly to library issue <A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-closed.html#350">350</A>, which will 
need to be reexamined if the CopyConstructible requirements change. </P>
<P><B>Proposed resolution:</B></P>
<P>Remove the last two rows of Table 30, eliminating the requirements that 
&amp;t and &amp;u return the address of t and u, respectively. </P>
<HR>
<A name=391>
<H3>391.&nbsp;non-member functions specified as const</H3></A>
<P><B>Section:</B>&nbsp;22.1.3.2 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.conversions">[lib.conversions]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#New">New</A>&nbsp; 
<B>Submitter:</B>&nbsp;James Kanze&nbsp; <B>Date:</B>&nbsp;10 Dec 2002</P>
<P>The specifications of toupper and tolower both specify the functions as 
const, althought they are not member functions, and are not specified as const 
in the header file synopsis in section 22.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-locales.html#lib.locales">[lib.locales]</A>. 
</P>
<P><B>Proposed resolution:</B></P>
<HR>
<A name=392>
<H3>392.&nbsp;'equivalence' for input iterators</H3></A>
<P><B>Section:</B>&nbsp;24.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.input.iterators">[lib.input.iterators]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#New">New</A>&nbsp; 
<B>Submitter:</B>&nbsp;Corwin Joy&nbsp; <B>Date:</B>&nbsp;11 Dec 2002</P>
<P>In section 24.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.input.iterators">[lib.input.iterators]</A> 
table 72 - 'Input Iterator Requirements' we have as a postcondition of *a: "If 
a==b and (a, b) is in the domain of == then *a is equivalent to *b". </P>
<P>In section 24.5.3.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.istreambuf.iterator::equal">[lib.istreambuf.iterator::equal]</A> 
it states that "istreambuf_iterator::equal returns true if and only if both 
iterators are at end-of-stream, or neither is at end-of-stream, <I>regardless of 
what streambuf object they use</I>." (My emphasis). </P>
<P>The defect is that either 'equivalent' needs to be more precisely defined or 
the conditions for equality in 24.5.3.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.istreambuf.iterator::equal">[lib.istreambuf.iterator::equal]</A> 
are incorrect. (Or both). </P>
<P>Consider the following example:</P><PRE>   #include &lt;iostream&gt;
   #include &lt;fstream&gt;
   #include &lt;iterator&gt;
   using namespace std;

   int main() {
    ifstream file1("file1.txt"), file2("file2.txt");
    istreambuf_iterator&lt;char&gt; f1(file1), f2(file2);
    cout &lt;&lt; "f1 == f2 : " &lt;&lt; boolalpha &lt;&lt; (f1 == f2) &lt;&lt; endl;
    cout &lt;&lt; "f1 = " &lt;&lt; *f1 &lt;&lt; endl;
    cout &lt;&lt; "f2 = " &lt;&lt; *f2 &lt;&lt; endl;
    return 0;
   }
</PRE>
<P>Now assuming that neither f1 or f2 are at the end-of-stream then f1 == f2 by 
24.5.3.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iterators.html#lib.istreambuf.iterator::equal">[lib.istreambuf.iterator::equal]</A>.</P>
<P>However, it is unlikely that *f1 will give the same value as *f2 except by 
accident.</P>
<P>So what does *f1 'equivalent' to *f2 mean? I think the standard should be 
clearer on this point, or at least be explicit that this does not mean that *f1 
and *f2 are required to have the same value in the case of input iterators.</P>
<P><B>Proposed resolution:</B></P>
<HR>
<A name=394>
<H3>394.&nbsp;behavior of formatted output on failure</H3></A>
<P><B>Section:</B>&nbsp;27.6.2.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.ostream.formatted">[lib.ostream.formatted]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#New">New</A>&nbsp; 
<B>Submitter:</B>&nbsp;Martin Sebor&nbsp; <B>Date:</B>&nbsp;27 Dec 2002</P>
<P>There is a contradiction in Formatted output about what bit is supposed to be 
set if the formatting fails. On sentence says it's badbit and another that it's 
failbit. </P>
<P>27.6.2.5.1, p1 says in the Common Requirements on Formatted output functions: 
<PRE>     ... If the generation fails, then the formatted output function
     does setstate(ios::failbit), which might throw an exception.
</PRE>
<P></P>
<P>27.6.2.5.2, p1 goes on to say this about Arithmetic Inserters: </P>
<P>... The formatting conversion occurs as if it performed the following code 
fragment: </P>
<P><PRE>     bool failed =
         use_facet&lt;num_put&lt;charT,ostreambuf_iterator&lt;charT,traits&gt;
         &gt; &gt;
         (getloc()).put(*this, *this, fill(), val). failed();

     ... If failed is true then does setstate(badbit) ...
</PRE>
<P></P>
<P>The original intent of the text, according to Jerry Schwarz (see 
c++std-lib-10500), is captured in the following paragraph: </P>
<P>In general "badbit" should mean that the stream is unusable because of some 
underlying failure, such as disk full or socket closure; "failbit" should mean 
that the requested formatting wasn't possible because of some inconsistency such 
as negative widths. So typically if you clear badbit and try to output something 
else you'll fail again, but if you clear failbit and try to output something 
else you'll succeed. </P>
<P>In the case of the arithmetic inserters, since num_put cannot report failure 
by any means other than exceptions (in response to which the stream must set 
badbit, which prevents the kind of recoverable error reporting mentioned above), 
the only other detectable failure is if the iterator returned from num_put 
returns true from failed(). </P>
<P>Since that can only happen (at least with the required iostream 
specializations) under such conditions as the underlying failure referred to 
above (e.g., disk full), setting badbit would seem to be the appropriate 
response (indeed, it is required in 27.6.2.5.2, p1). It follows that failbit can 
never be directly set by the arithmetic (it can only be set by the sentry object 
under some unspecified conditions). </P>
<P>The situation is different for other formatted output functions which can 
fail as a result of the streambuf functions failing (they may do so by means 
other than exceptions), and which are then required to set failbit. </P>
<P>The contradiction, then, is that ostream::operator&lt;&lt;(int) will set 
badbit if the disk is full, while operator&lt;&lt;(ostream&amp;, char) will set 
failbit under the same conditions. To make the behavior consistent, the Common 
requirements sections for the Formatted output functions should be changed as 
proposed below. </P>
<P><B>Proposed resolution:</B></P>
<P>Change the wording in the third sentence of the Common requirements section 
for the Formatted output functions in 27.6.2.5.1, p1 to: </P>
<P>... If the generation fails, then the formatted output function does 
setstate(ios::badbit), which might throw an exception. </P>
<HR>
<A name=395>
<H3>395.&nbsp;inconsistencies in the definitions of rand() and 
random_shuffle()</H3></A>
<P><B>Section:</B>&nbsp;26.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.c.math">[lib.c.math]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#New">New</A>&nbsp; 
<B>Submitter:</B>&nbsp;James Kanze&nbsp; <B>Date:</B>&nbsp;3 Jan 2003</P>
<P>In 26.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-numerics.html#lib.c.math">[lib.c.math]</A>, 
the C++ standard refers to the C standard for the definition of rand(); in the C 
standard, it is written that "The implementation shall behave as if no library 
function calls the rand function." </P>
<P>In 25.2.11 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-algorithms.html#lib.alg.random.shuffle">[lib.alg.random.shuffle]</A>, 
there is no specification as to how the two parameter version of the function 
generates its random value. I believe that all current implementations in fact 
call rand() (in contradiction with the requirement avove); if an implementation 
does not call rand(), there is the question of how whatever random generator it 
does use is seeded. Something is missing. </P>
<P><B>Proposed resolution:</B></P>
<P>In [lib.c.math], add a paragraph specifying that the C definition of rand 
shal be modified to say that "Unless otherwise specified, the implementation 
shall behave as if no library function calls the rand function." </P>
<P>In [lib.alg.random.shuffle], add a sentence to the effect that "The two 
argument form of the function is the equivalent of calling the three parameter 
form with the function rand [lib.c.math] as the third parameter. [Note: if the 
number of elements in the sequence is larger than RAND_MAX, this may result in a 
less than random shuffling.]" </P>
<P>Formally speaking, the note is probably not necessary, but it does make it 
clear that we were aware of the limitation, decided that it wasn't worth doing 
anything else about it, and that's life -- if you have more elements, it's your 
problem. (There are some good solutions to this in boost, but it's not yet 
appropriate to mention them in the standard.) </P>
<HR>
<A name=396>
<H3>396.&nbsp;what are characters zero and one</H3></A>
<P><B>Section:</B>&nbsp;23.3.5.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-containers.html#lib.bitset.cons">[lib.bitset.cons]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#New">New</A>&nbsp; 
<B>Submitter:</B>&nbsp;Martin Sebor&nbsp; <B>Date:</B>&nbsp;5 Jan 2003</P>
<P>23.3.5.1, p6 [lib.bitset.cons] talks about a generic character having the 
value of 0 or 1 but there is no definition of what that means for charT other 
than char and wchar_t. And even for those two types, the values 0 and 1 are not 
actually what is intended -- the values '0' and '1' are. This, along with the 
converse problem in the description of to_string() in 23.3.5.2, p33, looks like 
a defect remotely related to DR 303. </P>
<P>http://anubis.dkuug.dk/jtc1/sc22/wg21/docs/lwg-defects.html#303 </P><PRE>23.3.5.1:
  -6-  An element of the constructed string has value zero if the
       corresponding character in str, beginning at position pos,
       is 0. Otherwise, the element has the value one.
    </PRE><PRE>23.3.5.2:
  -33-  Effects: Constructs a string object of the appropriate
        type and initializes it to a string of length N characters.
        Each character is determined by the value of its
        corresponding bit position in *this. Character position N
        ?- 1 corresponds to bit position zero. Subsequent decreasing
        character positions correspond to increasing bit positions.
        Bit value zero becomes the character 0, bit value one becomes
        the character 1.
    </PRE>
<P>Also note the typo in 23.3.5.1, p6: the object under construction is a 
bitset, not a string. </P>
<P><B>Proposed resolution:</B></P>
<P>Provide additional arguments to both functions for the characters zero and 
one with default values of charT ('0') and charT ('1') like so: </P><PRE>template &lt;class charT, class traits, class Allocator&gt;
explicit
bitset(const basic_string&lt;charT, traits, Allocator&gt;&amp; str,
  typename basic_string&lt;charT, traits, Allocator&gt;::size_type pos = 0,
  typename basic_string&lt;charT, traits, Allocator&gt;::size_type n =
    basic_string&lt;charT, traits, Allocator&gt;::npos,
  const charT &amp;zero = charT ('0'),
  const charT &amp;one = charT ('1'));
    </PRE>
<P>and change the text of the second sentence in 23.3.5.1, p5 to read: </P>
<P>The function then throws invalid_argument if any of the rlen characters in 
str beginning at position pos is other than zero or one. The function uses 
traits::eq() to compare the character values. </P>
<P>and change the first two sentences in 23.3.5.1, p6 to read: </P>
<P>An element of the constructed bitset has the value false if the corresponding 
character in str, beginning at position pos, is equal to zero. Otherwise, the 
element is assigned the value true. </P>
<P>and </P><PRE>template &lt;class charT, class traits, class Allocator&gt;
basic_string&lt;charT, traits, Allocator&gt;
to_string(const charT &amp;zero = charT ('0'),
          const charT &amp;one = charT ('1')) const;
    </PRE>
<P>and change the effects clause in 23.3.5.2, p33 to read </P>
<P>Effects: Constructs a string object of the appropriate type and initializes 
it to a string of length N characters. Each character is determined by the value 
of its corresponding bit position in *this. Character position N -? 1 
corresponds to bit position zero. Subsequent decreasing character positions 
correspond to increasing bit positions. Bit value false becomes the character 
zero, bit value true becomes the character one. </P>
<HR>
<A name=397>
<H3>397.&nbsp;ostream::sentry dtor throws exceptions</H3></A>
<P><B>Section:</B>&nbsp;27.6.2.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.ostream::sentry">[lib.ostream::sentry]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#New">New</A>&nbsp; 
<B>Submitter:</B>&nbsp;Martin Sebor&nbsp; <B>Date:</B>&nbsp;5 Jan 2003</P>
<P>17.4.4.8, p3 prohibits library dtors from throwing exceptions. </P>
<P>27.6.2.3, p4 says this about the ostream::sentry dtor: </P><PRE>    -4- If ((os.flags() &amp; ios_base::unitbuf) &amp;&amp; !uncaught_exception())
        is true, calls os.flush().
    </PRE>
<P>27.6.2.6, p7 that describes ostream::flush() says: </P><PRE>    -7- If rdbuf() is not a null pointer, calls rdbuf()-&gt;pubsync().
        If that function returns ?-1 calls setstate(badbit) (which
        may throw ios_base::failure (27.4.4.3)).
    </PRE>
<P>That seems like a defect, since both pubsync() and setstate() can throw an 
exception. </P>
<P><B>Proposed resolution:</B></P>
<P>Add immediately after 27.6.2.3, p4: </P>
<P>If an exception is thrown during the execution of the function the exception 
is caught and the function calls setstate(badbit) (which is done without causing 
ios_base::failure to be thrown). </P>
<HR>
<A name=398>
<H3>398.&nbsp;effects of end-of-file on unformatted input functions</H3></A>
<P><B>Section:</B>&nbsp;27.6.2.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.ostream::sentry">[lib.ostream::sentry]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#New">New</A>&nbsp; 
<B>Submitter:</B>&nbsp;Martin Sebor&nbsp; <B>Date:</B>&nbsp;5 Jan 2003</P>
<P>While reviewing unformatted input member functions of istream for their 
behavior when they encounter end-of-file during input I found that the 
requirements vary, sometimes unexpectedly, and in more than one case even 
contradict established practice (GNU libstdc++ 3.2, IBM VAC++ 6.0, STLPort 4.5, 
SunPro 5.3, HP aCC 5.38, Rogue Wave libstd 3.1, and Classic Iostreams). </P>
<P>The following unformatted input member functions set eofbit if they encounter 
an end-of-file (this is the expected behavior, and also the behavior of all 
major implementations): </P>
<P><PRE>    basic_istream&lt;charT, traits&gt;&amp;
    get (char_type*, streamsize, char_type);
    </PRE>
<P></P>
<P>Also sets failbit if it fails to extract any characters. </P>
<P><PRE>    basic_istream&lt;charT, traits&gt;&amp;
    get (char_type*, streamsize);
    </PRE>
<P></P>
<P>Also sets failbit if it fails to extract any characters. </P>
<P><PRE>    basic_istream&lt;charT, traits&gt;&amp;
    getline (char_type*, streamsize, char_type);
    </PRE>
<P></P>
<P>Also sets failbit if it fails to extract any characters. </P>
<P><PRE>    basic_istream&lt;charT, traits&gt;&amp;
    getline (char_type*, streamsize);
    </PRE>
<P></P>
<P>Also sets failbit if it fails to extract any characters. </P>
<P><PRE>    basic_istream&lt;charT, traits&gt;&amp;
    ignore (int, int_type);
    </PRE>
<P></P>
<P><PRE>    basic_istream&lt;charT, traits&gt;&amp;
    read (char_type*, streamsize);
    </PRE>
<P></P>
<P>Also sets failbit if it encounters end-of-file. </P>
<P><PRE>    streamsize readsome (char_type*, streamsize);
    </PRE>
<P></P>
<P>The following unformated input member functions set failbit but not eofbit if 
they encounter an end-of-file (I find this odd since the functions make it 
impossible to distinguish a general failure from a failure due to end-of-file; 
the requirement is also in conflict with all major implementation which set both 
eofbit and failbit): </P>
<P><PRE>    int_type get();
    </PRE>
<P></P>
<P><PRE>    basic_istream&lt;charT, traits&gt;&amp;
    get (char_type&amp;);
    </PRE>
<P></P>
<P>These functions only set failbit of they extract no characters, otherwise 
they don't set any bits, even on failure (I find this inconsistency quite 
unexpected; the requirement is also in conflict with all major implementations 
which set eofbit whenever they encounter end-of-file): </P>
<P><PRE>    basic_istream&lt;charT, traits&gt;&amp;
    get (basic_streambuf&lt;charT, traits&gt;&amp;, char_type);
    </PRE>
<P></P>
<P><PRE>    basic_istream&lt;charT, traits&gt;&amp;
    get (basic_streambuf&lt;charT, traits&gt;&amp;);
    </PRE>
<P></P>
<P>This function sets no bits (all implementations except for STLport and 
Classic Iostreams set eofbit when they encounter end-of-file): </P>
<P><PRE>    int_type peek ();
    </PRE>
<P></P>
<P><B>Proposed resolution:</B></P>
<P>I propose that the requirements on all the functions be made consistent with 
one another as well as with (the majority of) existing implementations in that 
they all be required to set failbit if they fail for any reason other than due 
to an exception (with badbit still being required to be set if an exception 
occurs during input), and to set eofbit when they encounter end-of-file. </P>
<P>Specifically, I propose the following set of changes: </P>
<P>Replace the Effects clause in 27.6.1.3, p3 with </P>
<P><PRE>    Effects: Behaves as an unformatted input function (as described
    in 27.6.1.3, paragraph 1). After constructing a sentry object,
    extracts a character c, if one is available. Otherwise, the
    function calls setstate(eofbit | failbit), which may throw
    ios_base::failure (27.4.4.3).
    </PRE>
<P></P>
<P>Replace the Effects clause in 27.6.1.3, p5 with </P>
<P><PRE>    Effects: Behaves as an unformatted input function (as described
    in 27.6.1.3, paragraph 1). After constructing a sentry object,
    extracts a character, if one is available, and assigns it to c.
    285) Otherwise, the function calls setstate(eofbit | failbit)
    (which may throw ios_base::failure (27.4.4.3)).
    </PRE>
<P></P>
<P>Replace the first bullet of 27.6.1.3, p12 with </P>
<P><PRE>    --  end-of-file occurs on the input sequence (in which case
        the function calls setstate(eofbit));
    </PRE>
<P></P>
<P>Replace the third bullet of 27.6.1.3, p12 with </P>
<P><PRE>    --  an exception occurs
    </PRE>
<P></P>
<P>(I.e., have the function behave like all other unformatted input functions 
WRT exceptions -- set badbit and propagate the original exception if (badbit 
&amp; exceptions()) is non-zero). </P>
<P>Add an Effects clause after 27.6.1.3, p27: </P>
<P><PRE>   Effects: If (traits_type::eq_int_type(rdbuf()-&gt;sgetc(), traits_type::eof())
   evaluates to true, the function calls setstate(eofbit).
    </PRE>
<P></P>
<HR>
<A name=399>
<H3>399.&nbsp;volations of unformatted input function requirements</H3></A>
<P><B>Section:</B>&nbsp;27.6.1.3 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-iostreams.html#lib.istream.unformatted">[lib.istream.unformatted]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#New">New</A>&nbsp; 
<B>Submitter:</B>&nbsp;Martin Sebor&nbsp; <B>Date:</B>&nbsp;5 Jan 2003</P>
<P>The Effects clauses for the two functions below violate the general 
requirements on unformatted input functions outlined in 27.6.1.3: they do not 
begin by constructing a sentry object. Instead, they begin by calling widen 
('\n'), which may throw an exception. The exception is then allowed to propagate 
from the unformatted input function irrespective of the setting of exceptions(). 
</P>
<P>Note that in light of 27.6.1.1, p3 and p4, the fact that the functions allow 
exceptions thrown from widen() to propagate may not strictly speaking be a 
defect (but the fact that the functions do not start by constructing a sentry 
object still is). However, since an exception thrown from ctype&lt;charT&gt; 
::widen() during any other input operation (say, from within a call to 
num_get&lt;charT&gt;::get()) will be caught and cause badbit to be set, these 
two functions should not be treated differently for the sake of consistency. 
</P>
<P><B>Proposed resolution:</B></P>
<P>Proposed resolution: Replace the Effects clauses in the two paragraphs below 
with Returns clauses and strike the subsequent paragraphs. Specifically, 
<P></P>in 27.6.1.3, p10, replace 
<P></P>
<P><PRE>   basic_istream&lt;charT, traits&gt;&amp;
   get (char_type *s, streamsize n)
   -10- Effects: Calls get (s, n, widen ('\n'))
   -11- Returns: Value returned by the call.
    </PRE>
<P></P>
<P>with </P>
<P><PRE>   basic_istream&lt;charT, traits&gt;&amp;
   get (char_type *s, streamsize n)
   -10- Returns: get (s, n, widen ('\n')).
    </PRE>
<P></P>
<P>and in 27.6.1.3, p15, replace </P>
<P><PRE>   basic_istream&lt;charT, traits&gt;&amp;
   get(basic_streambuf&lt;char_type, traits&gt;&amp; sb);
   -15- Effects: Calls get (sb, n, widen ('\n'))
   -16- Returns: Value returned by the call.
    </PRE>
<P></P>
<P>with </P>
<P><PRE>   basic_istream&lt;charT, traits&gt;&amp;
   get(basic_streambuf&lt;char_type, traits&gt;&amp; sb);
   -15- Returns: get (sb, n, widen ('\n')).
    </PRE>
<P></P>
<P>This change brings the requirements on these two functions in accord with 
those on getline() in 27.6.1.3, p12 which is correctly described by a Returns 
clause (not an Effects clause). </P>
<HR>
<A name=400>
<H3>400.&nbsp;redundant type cast in lib.allocator.members</H3></A>
<P><B>Section:</B>&nbsp;20.4.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-utilities.html#lib.allocator.members">[lib.allocator.members]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#New">New</A>&nbsp; 
<B>Submitter:</B>&nbsp;Markus Mauhart&nbsp; <B>Date:</B>&nbsp;27 Feb 2003</P>
<P>20.4.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-utilities.html#lib.allocator.members">[lib.allocator.members]</A> 
allocator members, contains the following 3 lines: </P><PRE>  12 Returns: new((void *) p) T( val)
     void destroy(pointer p);
  13 Returns: ((T*) p)-&gt;~T()
</PRE>
<P>The type cast "(T*) p" in the last line is redundant cause we know that 
std::allocator&lt;T&gt;::pointer is a typedef for T*. </P>
<P><B>Proposed resolution:</B></P>
<P>Replace "((T*) p)" with "p". </P>
<HR>
<A name=401>
<H3>401.&nbsp; incorrect type casts in table 32 in 
lib.allocator.requirements</H3></A>
<P><B>Section:</B>&nbsp;20.1.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-utilities.html#lib.allocator.requirements">[lib.allocator.requirements]</A>&nbsp; 
<B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#New">New</A>&nbsp; 
<B>Submitter:</B>&nbsp;Markus Mauhart&nbsp; <B>Date:</B>&nbsp;27 Feb 2003</P>
<P>I think that in par2 of 20.1.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-utilities.html#lib.allocator.requirements">[lib.allocator.requirements]</A> 
the last two lines of table 32 contain two incorrect type casts. The lines are 
... </P><PRE>  a.construct(p,t)   Effect: new((void*)p) T(t)
  a.destroy(p)       Effect: ((T*)p)?-&gt;~T()
</PRE>
<P>.... with the prerequisits coming from the preceding two paragraphs, 
especially from table 31: </P><PRE>  alloc&lt;T&gt;             a     ;// an allocator for T
  alloc&lt;T&gt;::pointer    p     ;// random access iterator
                              // (may be different from T*)
  alloc&lt;T&gt;::reference  r = *p;// T&amp;
  T const&amp;             t     ;
</PRE>
<P>For that two type casts ("(void*)p" and "(T*)p") to be well-formed this would 
require then conversions to T* and void* for all alloc&lt;T&gt;::pointer, so it 
would implicitely introduce extra requirements for alloc&lt;T&gt;::pointer, 
additionally to the only current requirement (being a random access iterator). 
</P>
<P><B>Proposed resolution:</B></P>
<P>"(void*)p" should be replaced with "(void*)&amp;*p" and that "((T*)p)?-&gt;" 
should be replaced with "(*p)." or with "(&amp;*p)-&gt;". </P>
<P>Note: Actually I would prefer to replace "((T*)p)?-&gt;dtor_name" with 
"p?-&gt;dtor_name", but AFAICS this is not possible cause of an omission in 
13.5.6 <A 
href="file:///P:/j16/33-pre-oxford/lwg/over.html#over.ref">[over.ref]</A> (for 
which I have filed another DR on 29.11.2002). </P>
<HR>
<A name=402>
<H3>402.&nbsp;wrong new expression in [some_]allocator::construct</H3></A>
<P><B>Section:</B>&nbsp;20.1.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-utilities.html#lib.allocator.requirements">[lib.allocator.requirements]</A>, 
20.4.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-utilities.html#lib.allocator.members">[lib.allocator.members]</A>, 
&nbsp; <B>Status:</B>&nbsp;<A 
href="file:///P:/j16/33-pre-oxford/lwg/lwg-active.html#New">New</A>&nbsp; 
<B>Submitter:</B>&nbsp;Markus Mauhart&nbsp; <B>Date:</B>&nbsp;27 Feb 2003</P>
<P>This applies to the new expression that is contained in both par12 of 
20.4.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-utilities.html#lib.allocator.members">[lib.allocator.members]</A> 
and in par2 (table 32) of 20.1.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-utilities.html#lib.allocator.requirements">[lib.allocator.requirements]</A>. 
I think this new expression is wrong, involving unintended side effects. </P>
<P>20.4.1.1 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-utilities.html#lib.allocator.members">[lib.allocator.members]</A> 
contains the following 3 lines:</P><PRE>  11 Returns: the largest value N for which the call allocate(N,0) might succeed.
     void construct(pointer p, const_reference val);
  12 Returns: new((void *) p) T( val)
</PRE>
<P>20.1.5 <A 
href="file:///P:/j16/33-pre-oxford/lwg/lib-utilities.html#lib.allocator.requirements">[lib.allocator.requirements]</A> 
in table 32 has the following line:</P><PRE>  a.construct(p,t)   Effect: new((void*)p) T(t)
</PRE>
<P>.... with the prerequisits coming from the preceding two paragraphs, 
especially from table 31: </P><PRE>  alloc&lt;T&gt;             a     ;// an allocator for T
  alloc&lt;T&gt;::pointer    p     ;// random access iterator
                              // (may be different from T*)
  alloc&lt;T&gt;::reference  r = *p;// T&amp;
  T const&amp;             t     ;
</PRE>
<P>Cause of using "new" but not "::new", any existing "T::operator new" function 
will hide the global placement new function. When there is no "T::operator new" 
with adequate signature, every_alloc&lt;T&gt;::construct(..) is ill-formed, and 
most std::container&lt;T,every_alloc&lt;T&gt;&gt; use it; a workaround would be 
adding placement new and delete functions with adequate signature and semantic 
to class T, but class T might come from another party. Maybe even worse is the 
case when T has placement new and delete functions with adequate signature but 
with "unknown" semantic: I dont like to speculate about it, but whoever 
implements any_container&lt;T,any_alloc&gt; and wants to use construct(..) 
probably must think about it. </P>
<P><B>Proposed resolution:</B></P>
<P>Therefore I think that "new" should be replaced with "::new" in both cases. 
</P>
<P>----- End of document -----</P></BODY></HTML>
