checked_delete.hpp documentation added.

[SVN r16238]
This commit is contained in:
Peter Dimov 2002-11-14 14:53:32 +00:00
parent 2b7d10aceb
commit 32fb45eba9
4 changed files with 267 additions and 197 deletions

124
checked_delete.html Normal file
View File

@ -0,0 +1,124 @@
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
<html>
<head>
<title>Boost: checked_delete.hpp documentation</title>
<meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
</head>
<body bgcolor="white" style="MARGIN-LEFT: 5%; MARGIN-RIGHT: 5%">
<table border="0" width="100%">
<tr>
<td width="277">
<img src="../../c++boost.gif" alt="c++boost.gif (8819 bytes)" width="277" height="86">
</td>
<td align="middle">
<h1>checked_delete.hpp</h1>
</td>
</tr>
<tr>
<td colspan="2" height="64">&nbsp;</td>
</tr>
</table>
<p>
The header <STRONG>&lt;boost/checked_delete.hpp&gt;</STRONG> defines two
function templates, <STRONG>checked_delete</STRONG> and <STRONG>checked_array_delete</STRONG>,
and two class templates, <STRONG>checked_deleter</STRONG> and <STRONG>checked_array_deleter</STRONG>.
</p>
<P>The C++ Standard allows, in 5.3.5/5, pointers to incomplete class types to
be deleted with a <EM>delete-expression</EM>. When the class has a non-trivial
destructor, or a class-specific operator delete, the behavior is undefined.
Some compilers issue a warning when an incomplete type is deleted, but
unfortunately, not all do, and programmers sometimes ignore or disable
warnings.</P>
<P>A particularly troublesome case is when a smart pointer's destructor, such as <STRONG>
boost::scoped_ptr&lt;T&gt;::~scoped_ptr</STRONG>, is instantiated with an
incomplete type. This can often lead to silent, hard to track failures.</P>
<P>The supplied function and class templates can be used to prevent these problems,
as they require a complete type, and cause a compilation error otherwise.</P>
<h3><a name="Synopsis">Synopsis</a></h3>
<pre>
namespace boost
{
template&lt;class T&gt; void checked_delete(T * p);
template&lt;class T&gt; void checked_array_delete(T * p);
template&lt;class T&gt; struct checked_deleter;
template&lt;class T&gt; struct checked_array_deleter;
}
</pre>
<h3>checked_delete</h3>
<h4><a name="checked_delete">template&lt;class T&gt; void checked_delete(T * p);</a></h4>
<blockquote>
<p>
<b>Requires:</b> <b>T</b> must be a complete type. The expression <tt>delete p</tt>
must be well-formed.
</p>
<p>
<b>Effects:</b> <tt>delete p;</tt>
</p>
</blockquote>
<h3>checked_array_delete</h3>
<h4><a name="checked_array_delete">template&lt;class T&gt; void checked_array_delete(T
* p);</a></h4>
<blockquote>
<p>
<b>Requires:</b> <b>T</b> must be a complete type. The expression <tt>delete [] p</tt>
must be well-formed.
</p>
<p>
<b>Effects:</b> <tt>delete [] p;</tt>
</p>
</blockquote>
<h3>checked_deleter</h3>
<pre>
template&lt;class T&gt; struct checked_deleter
{
typedef void result_type;
typedef T * argument_type;
void operator()(T * p);
};
</pre>
<h4>void checked_deleter&lt;T&gt;::operator()(T * p);</h4>
<blockquote>
<p>
<b>Requires:</b> <b>T</b> must be a complete type. The expression <tt>delete p</tt>
must be well-formed.
</p>
<p>
<b>Effects:</b> <tt>delete p;</tt>
</p>
</blockquote>
<h3>checked_array_deleter</h3>
<pre>
template&lt;class T&gt; struct checked_array_deleter
{
typedef void result_type;
typedef T * argument_type;
void operator()(T * p);
};
</pre>
<h4>void checked_array_deleter&lt;T&gt;::operator()(T * p);</h4>
<blockquote>
<p>
<b>Requires:</b> <b>T</b> must be a complete type. The expression <tt>delete [] p</tt>
must be well-formed.
</p>
<p>
<b>Effects:</b> <tt>delete [] p;</tt>
</p>
</blockquote>
<h3><a name="Acknowledgements">Acknowledgements</a></h3>
<p>
The function templates <STRONG>checked_delete</STRONG> and <STRONG>checked_array_delete</STRONG>
were originally part of <STRONG>&lt;boost/utility.hpp&gt;</STRONG>, and the
documentation acknowledged Beman Dawes, Dave Abrahams, Vladimir Prus,
Rainer Deyke, John Maddock, and others as contributors.
</p>
<p>
<br>
<small>Copyright © 2002 by Peter Dimov. Permission to copy, use, modify, sell
and distribute this document is granted provided this copyright notice appears
in all copies. This document is provided "as is" without express or implied
warranty, and with no claim as to its suitability for any purpose.</small></p>
</body>
</html>

View File

@ -9,12 +9,15 @@
// boost/checked_delete.hpp // boost/checked_delete.hpp
// //
// Copyright (c) 1999, 2000, 2001, 2002 boost.org // Copyright (c) 1999, 2000, 2001, 2002 boost.org
// Copyright (c) 2002 Peter Dimov
// //
// Permission to copy, use, modify, sell and distribute this software // Permission to copy, use, modify, sell and distribute this software
// is granted provided this copyright notice appears in all copies. // is granted provided this copyright notice appears in all copies.
// This software is provided "as is" without express or implied // This software is provided "as is" without express or implied
// warranty, and with no claim as to its suitability for any purpose. // warranty, and with no claim as to its suitability for any purpose.
// //
// http://www.boost.org/libs/utility/checked_delete.html
//
namespace boost namespace boost
{ {

View File

@ -1,34 +1,31 @@
<html> <html>
<head>
<head> <meta http-equiv="Content-Language" content="en-us">
<meta http-equiv="Content-Language" content="en-us"> <meta name="GENERATOR" content="Microsoft FrontPage 5.0">
<meta name="GENERATOR" content="Microsoft FrontPage 5.0"> <meta name="ProgId" content="FrontPage.Editor.Document">
<meta name="ProgId" content="FrontPage.Editor.Document"> <meta http-equiv="Content-Type" content="text/html; charset=windows-1252">
<meta http-equiv="Content-Type" content="text/html; charset=windows-1252"> <title>Boost Utility Library</title>
<title>Boost Utility Library</title> </head>
</head> <body bgcolor="#FFFFFF">
<h1><IMG SRC="../../c++boost.gif" WIDTH="276" HEIGHT="86" align="center">Boost
<body bgcolor="#FFFFFF"> Utility Library</h1>
<p>The Boost Utility Library isn't really a single library at all. It is just
<h1><IMG SRC="../../c++boost.gif" WIDTH="276" HEIGHT="86" align="center">Boost a collection for components too small to be called libraries in their own
Utility Library</h1> right.</p>
<p>The Boost Utility Library isn't really a single library at all.&nbsp; It is <p>But that doesn't mean there isn't useful stuff here. Take a look:</p>
just a collection for components too small to be called libraries in their own <blockquote>
right.</p> <p><a href="base_from_member.html">base_from_member</a><br>
<p>But that doesn't mean there isn't useful stuff here.&nbsp; Take a look:</p> <a href="call_traits.htm">call_traits.htm</a><br>
<blockquote> <a href="checked_delete.html">checked_delete.html</a><br>
<p><a href="base_from_member.html">base_from_member</a><br> <a href="compressed_pair.htm">compressed_pair.htm</a><br>
<a href="call_traits.htm">call_traits.htm</a><br> <a href="operators.htm">operators.htm</a><br>
<a href="compressed_pair.htm">compressed_pair.htm</a><br> <a href="tie.html">tie</a><br>
<a href="operators.htm">operators.htm</a><br> <a href="utility.htm">utility.htm</a></p>
<a href="tie.html">tie</a><br> </blockquote>
<a href="utility.htm">utility.htm</a></p> <hr>
</blockquote> <p>Revised
<hr> <!--webbot bot="Timestamp" S-Type="EDITED" S-Format="%d %B, %Y" startspan -->
<p>Revised 07 May, 2002<!--webbot bot="Timestamp" endspan i-checksum="13976" --></p>
<!--webbot bot="Timestamp" S-Type="EDITED" S-Format="%d %B, %Y" startspan -->07 May, 2002<!--webbot bot="Timestamp" endspan i-checksum="13976" --></p> <p>&nbsp;</p>
<p>&nbsp;</p> </body>
</body>
</html> </html>

View File

@ -1,168 +1,114 @@
<html> <html>
<head>
<head> <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
<meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1"> <title>Header boost/utility.hpp Documentation</title>
<title>Header boost/utility.hpp Documentation</title> </head>
</head> <body bgcolor="#FFFFFF" text="#000000">
<h1><img src="../../c++boost.gif" alt="c++boost.gif (8819 bytes)" align="center" WIDTH="277" HEIGHT="86">Header
<body bgcolor="#FFFFFF" text="#000000"> <a href="../../boost/utility.hpp">boost/utility.hpp</a></h1>
<p>The entire contents of the header <code><a href="../../boost/utility.hpp">&lt;boost/utility.hpp&gt;</a></code>
<h1><img src="../../c++boost.gif" alt="c++boost.gif (8819 bytes)" align="center" WIDTH="277" HEIGHT="86">Header are in <code>namespace boost</code>.</p>
<a href="../../boost/utility.hpp">boost/utility.hpp</a></h1> <h2>Contents</h2>
<ul>
<p>The entire contents of the header <code><a href="../../boost/utility.hpp">&lt;boost/utility.hpp&gt;</a></code> <li>
are in <code>namespace boost</code>.</p> Class templates supporting the <a href="base_from_member.html">base-from-member
idiom</a></li>
<h2>Contents</h2> <li>
Function templates <a href="#checked_delete">checked_delete() and
<ul> checked_array_delete()</a></li>
<li>Class templates supporting the <a href="base_from_member.html">base-from-member <li>
idiom</a></li> Function templates <a href="#functions next">next() and prior()</a></li>
<li>Function templates <a href="#checked_delete">checked_delete() and <li>
checked_array_delete()</a></li> Class <a href="#Class noncopyable">noncopyable</a></li>
<li>Function templates <a href="#functions next">next() and prior()</a></li> <li>
<li>Class <a href="#Class noncopyable">noncopyable</a></li> Function template <a href="#addressof">addressof()</a></li>
<li>Function template <a href="#addressof">addressof()</a></li> <li>
<li>Function template <a href="tie.html">tie()</a> and supporting class tied.</li> Function template <a href="tie.html">tie()</a> and supporting class tied.</li>
</ul> </ul>
<h2> Function templates <a name="checked_delete">checked_delete</a>() and <h2>
checked_array_delete()</h2> Function templates <a name="checked_delete">checked_delete</a>() and
checked_array_delete()</h2>
<p>Deletion of a pointer to an incomplete type is an unsafe programming practice <p>See <a href="checked_delete.html">separate documentation</a>.</p>
because there is no way for the compiler to verify that the destructor is indeed <h2>
trivial.&nbsp; The checked_delete() and checked_array_delete() function <a name="functions next">Function</a> templates next() and prior()</h2>
templates simply <b>delete</b> or <b>delete[]</b> their argument, but also <p>Certain data types, such as the C++ Standard Library's forward and bidirectional
require that their argument be a complete type.&nbsp; They issue an appropriate iterators, do not provide addition and subtraction via operator+() or
compiler error diagnostic if that requirement is not met.&nbsp; A typical operator-().&nbsp; This means that non-modifying computation of the next or
implementation is shown; other implementations may vary:</p> prior value requires a temporary, even though operator++() or operator--() is
provided.&nbsp; It also means that writing code like <code>itr+1</code> inside
<pre> template&lt; typename T &gt; a template restricts the iterator category to random access iterators.</p>
inline void checked_delete(T const volatile * x) <p>The next() and prior() functions provide a simple way around these problems:</p>
{ <blockquote>
BOOST_STATIC_ASSERT( sizeof(T) ); // assert type complete at point <pre>template &lt;class T&gt;
// of instantiation
delete x;
}
template&lt; typename T &gt;
inline void checked_array_delete(T const volatile * x)
{
BOOST_STATIC_ASSERT( sizeof(T) ); // assert type complete at point
// of instantiation
delete [] x;
}</pre>
<p>Contributed by Beman Dawes, based on a suggestion from Dave Abrahams,
generalizing an idea from Vladimir Prus, with comments from Rainer Deyke, John
Maddock, and others.</p>
<h3>Background</h3>
<p>The C++ Standard specifies that delete on a pointer to an incomplete types is
undefined behavior if the type has a non-trivial destructor in&nbsp; [expr.delete]
5.3.5 paragraph.&nbsp; No diagnostic is required.&nbsp; Some but not all
compilers issue warnings if the type is incomplete at point of deletion.</p>
<h2> <a name="functions next">Function</a> templates next() and prior()</h2>
<p>Certain data types, such as the C++ Standard Library's forward and
bidirectional iterators, do not provide addition and subtraction via operator+()
or operator-().&nbsp; This means that non-modifying computation of the next or
prior value requires a temporary, even though operator++() or operator--() is
provided.&nbsp; It also means that writing code like <code>itr+1</code> inside a
template restricts the iterator category to random access iterators.</p>
<p>The next() and prior() functions provide a simple way around these problems:</p>
<blockquote>
<pre>template &lt;class T&gt;
T next(T x) { return ++x; } T next(T x) { return ++x; }
template &lt;class X&gt; template &lt;class X&gt;
T prior(T x) { return --x; }</pre> T prior(T x) { return --x; }</pre>
</blockquote>
</blockquote> <p>Usage is simple:</p>
<blockquote>
<p>Usage is simple:</p> <pre>const std::list&lt;T&gt;::iterator p = get_some_iterator();
<blockquote>
<pre>const std::list&lt;T&gt;::iterator p = get_some_iterator();
const std::list&lt;T&gt;::iterator prev = boost::prior(p);</pre> const std::list&lt;T&gt;::iterator prev = boost::prior(p);</pre>
</blockquote>
</blockquote> <p>Contributed by <a href="../../people/dave_abrahams.htm">Dave Abrahams</a>.</p>
<h2><a name="Class noncopyable">Class noncopyable</a></h2>
<p>Contributed by <a href="../../people/dave_abrahams.htm">Dave Abrahams</a>.</p> <p>Class <strong>noncopyable</strong> is a base class.&nbsp; Derive your own class
from <strong>noncopyable</strong> when you want to prohibit copy construction
<h2><a name="Class noncopyable">Class noncopyable</a></h2> and copy assignment.</p>
<p>Some objects, particularly those which hold complex resources like files or
<p>Class <strong>noncopyable</strong> is a base class.&nbsp; Derive your own class from <strong>noncopyable</strong> network connections, have no sensible copy semantics.&nbsp; Sometimes there are
when you want to prohibit copy construction and copy assignment.</p> possible copy semantics, but these would be of very limited usefulness and be
very difficult to implement correctly.&nbsp; Sometimes you're implementing a
<p>Some objects, particularly those which hold complex resources like files or class that doesn't need to be copied just yet and you don't want to take the
network connections, have no sensible copy semantics.&nbsp; Sometimes there are time to write the appropriate functions.&nbsp; Deriving from <b>noncopyable</b>
possible copy semantics, but these would be of very limited usefulness and be will prevent the otherwise implicitly-generated functions (which don't have the
very difficult to implement correctly.&nbsp; Sometimes you're implementing a class that doesn't need to be copied proper semantics) from becoming a trap for other programmers.</p>
just yet and you don't want to take the time to write the appropriate functions.&nbsp; <p>The traditional way to deal with these is to declare a private copy constructor
Deriving from <b> noncopyable</b> will prevent the otherwise implicitly-generated and copy assignment, and then document why this is done.&nbsp; But deriving
functions (which don't have the proper semantics) from becoming a trap for other programmers.</p> from <b>noncopyable</b> is simpler and clearer, and doesn't require additional
documentation.</p>
<p>The traditional way to deal with these is to declare a private copy constructor and copy assignment, and then <p>The program <a href="noncopyable_test.cpp">noncopyable_test.cpp</a> can be used
document why this is done.&nbsp; But deriving from <b>noncopyable</b> is simpler to verify class <b>noncopyable</b> works as expected. It has have been run
and clearer, and doesn't require additional documentation.</p> successfully under GCC 2.95, Metrowerks CodeWarrior 5.0, and Microsoft Visual
C++ 6.0 sp 3.</p>
<p>The program <a href="noncopyable_test.cpp">noncopyable_test.cpp</a> can be <p>Contributed by <a href="../../people/dave_abrahams.htm">Dave Abrahams</a>.</p>
used to verify class <b>noncopyable</b> works as expected. It has have been run successfully under <h3>Example</h3>
GCC 2.95, Metrowerks <blockquote>
CodeWarrior 5.0, and Microsoft Visual C++ 6.0 sp 3.</p> <pre>// inside one of your own headers ...
<p>Contributed by <a href="../../people/dave_abrahams.htm">Dave Abrahams</a>.</p>
<h3>Example</h3>
<blockquote>
<pre>// inside one of your own headers ...
#include &lt;boost/utility.hpp&gt; #include &lt;boost/utility.hpp&gt;
class ResourceLadenFileSystem : boost::noncopyable { class ResourceLadenFileSystem : boost::noncopyable {
...</pre> ...</pre>
</blockquote> </blockquote>
<h3>Rationale</h3>
<h3>Rationale</h3> <p>Class noncopyable has protected constructor and destructor members to emphasize
<p>Class noncopyable has protected constructor and destructor members to that it is to be used only as a base class.&nbsp; Dave Abrahams notes concern
emphasize that it is to be used only as a base class.&nbsp; Dave Abrahams notes about the effect on compiler optimization of adding (even trivial inline)
concern about the effect on compiler optimization of adding (even trivial inline) destructor declarations. He says &quot;Probably this concern is misplaced,
destructor declarations. He says &quot;Probably this concern is misplaced, because because noncopyable will be used mostly for classes which own resources and
noncopyable will be used mostly for classes which own resources and thus have non-trivial destruction semantics.&quot;</p> thus have non-trivial destruction semantics.&quot;</p>
<h2><a name="addressof">Function template addressof()</a></h2> <h2><a name="addressof">Function template addressof()</a></h2>
<p>Function <strong>addressof()</strong> returns the address of an object.</p> <p>Function <strong>addressof()</strong> returns the address of an object.</p>
<blockquote>
<blockquote> <pre>
<pre>
template &lt;typename T&gt; inline T* addressof(T& v); template &lt;typename T&gt; inline T* addressof(T& v);
template &lt;typename T&gt; inline const T* addressof(const T& v); template &lt;typename T&gt; inline const T* addressof(const T& v);
template &lt;typename T&gt; inline volatile T* addressof(volatile T& v); template &lt;typename T&gt; inline volatile T* addressof(volatile T& v);
template &lt;typename T&gt; inline const volatile T* addressof(const volatile T& v); template &lt;typename T&gt; inline const volatile T* addressof(const volatile T& v);
</pre> </pre>
</blockquote> </blockquote>
<p>C++ allows programmers to replace the unary <strong>operator&()</strong> class
member used to get the address of an object. Getting the real address of an
<p>C++ allows programmers to replace the unary object requires ugly casting tricks to avoid invoking the overloaded <strong>operator&()</strong>.
<strong>operator&()</strong> class member used to get the address of Function <strong>addressof()</strong> provides a wrapper around the necessary
an object. Getting the real address of an object requires ugly code to make it easy to get an object's real address.
casting tricks to avoid invoking the overloaded </p>
<strong>operator&()</strong>. Function <strong>addressof()</strong> <p>The program <a href="addressof_test.cpp">addressof_test.cpp</a> can be used to
provides a wrapper around the necessary code to make it easy to get an verify that <b>addressof()</b> works as expected.</p>
object's real address. <p>Contributed by Brad King based on ideas from discussion with Doug Gregor.</p>
</p> <h3>Example</h3>
<blockquote>
<p>The program <a href="addressof_test.cpp">addressof_test.cpp</a> can be <pre>#include &lt;boost/utility.hpp&gt;
used to verify that <b>addressof()</b> works as expected.</p>
<p>Contributed by Brad King based on ideas from discussion with Doug Gregor.</p>
<h3>Example</h3>
<blockquote>
<pre>#include &lt;boost/utility.hpp&gt;
struct useless_type {}; struct useless_type {};
class nonaddressable { class nonaddressable {
@ -174,20 +120,20 @@ void f() {
nonaddressable* xp = boost::addressof(x); nonaddressable* xp = boost::addressof(x);
// nonaddressable* xpe = &amp;x; /* error */ // nonaddressable* xpe = &amp;x; /* error */
}</pre> }</pre>
</blockquote> </blockquote>
<h2>Class templates for the Base-from-Member Idiom</h2>
<h2>Class templates for the Base-from-Member Idiom</h2> <p>See <a href="base_from_member.html">separate documentation</a>.</p>
<p>See <a href="base_from_member.html">separate documentation</a>.</p> <h2>Function template tie()</h2>
<h2>Function template tie()</h2> <p>See <a href="tie.html">separate documentation</a>.</p>
<p>See <a href="tie.html">separate documentation</a>.</p> <hr>
<hr> <p>Revised&nbsp; <!--webbot bot="Timestamp" S-Type="EDITED" S-Format="%d %B, %Y" startspan
<p>Revised&nbsp; <!--webbot bot="Timestamp" S-Type="EDITED" S-Format="%d %B, %Y" startspan -->
-->10 September, 2001<!--webbot bot="Timestamp" endspan i-checksum="39328" 10 September, 2001<!--webbot bot="Timestamp" endspan i-checksum="39328"
--> -->
</p> </p>
<p>© Copyright boost.org 1999. Permission to copy, use, modify, sell and <p>© Copyright boost.org 1999-2002. Permission to copy, use, modify, sell and distribute
distribute this document is granted provided this copyright notice appears in this document is granted provided this copyright notice appears in all copies.
all copies. This document is provided &quot;as is&quot; without express or This document is provided &quot;as is&quot; without express or implied
implied warranty, and with no claim as to its suitability for any purpose.</p> warranty, and with no claim as to its suitability for any purpose.</p>
</body> </body>
</html> </html>