|
Boost-Commit : |
Subject: [Boost-commit] svn:boost r60080 - in sandbox/filesystem-v3/libs/filesystem: doc example
From: bdawes_at_[hidden]
Date: 2010-03-02 15:44:24
Author: bemandawes
Date: 2010-03-02 15:44:23 EST (Tue, 02 Mar 2010)
New Revision: 60080
URL: http://svn.boost.org/trac/boost/changeset/60080
Log:
Update tutorial programs to catch exceptions
Text files modified:
sandbox/filesystem-v3/libs/filesystem/doc/reference.html | 35 +++++--
sandbox/filesystem-v3/libs/filesystem/doc/tutorial.html | 191 +++++++++++++++++++++++++--------------
sandbox/filesystem-v3/libs/filesystem/example/tut1.cpp | 2
sandbox/filesystem-v3/libs/filesystem/example/tut2.cpp | 10 -
sandbox/filesystem-v3/libs/filesystem/example/tut3.cpp | 36 ++++---
sandbox/filesystem-v3/libs/filesystem/example/tut4.cpp | 44 +++++---
6 files changed, 200 insertions(+), 118 deletions(-)
Modified: sandbox/filesystem-v3/libs/filesystem/doc/reference.html
==============================================================================
--- sandbox/filesystem-v3/libs/filesystem/doc/reference.html (original)
+++ sandbox/filesystem-v3/libs/filesystem/doc/reference.html 2010-03-02 15:44:23 EST (Tue, 02 Mar 2010)
@@ -952,8 +952,11 @@
<pre>path <a name="path-filename">filename</a>() const;</pre>
<blockquote>
<p><i>Returns:</i> <code>empty() ? path() : *--end()</code></p>
- <p>[<i>Example:</i> <code>std::cout << path("/foo/bar.txt").filename();</code>
- outputs "<code>bar.txt</code>" (without the quotes). <i>--end example</i>]</p>
+ <p>[<i>Example:</i></p>
+ <blockquote>
+ <pre><code>std::cout << path("/foo/bar.txt").filename();</code> // outputs "<code>bar.txt</code>" (without the quotes)</pre>
+ </blockquote>
+ <p> <i>--end example</i>]</p>
</blockquote>
<pre>path <a name="path-stem">stem</a>(const path& p) const;</pre>
<blockquote>
@@ -963,8 +966,17 @@
ending at the last dot (the dot is not included). Otherwise,
returns <code>
p.filename()</code>.</p>
- <p>[<i>Example:</i> <code>std::cout << path("/foo/bar.txt").stem();</code>
- outputs "<code>bar</code>" (without the quotes). <i>--end example</i>]</p>
+ <p>[<i>Example:</i></p>
+ <blockquote>
+ <pre><code>std::cout << path("/foo/bar.txt").stem();</code> // outputs "<code>bar</code>" (without the quotes)</pre>
+ <pre>path p = "foo.bar.baz.tar";
+for (; !p.extension().empty(); p = p.stem())
+ std::cout << p.extension() << '\n';
+ // outputs: .tar
+ // .baz
+ // .bar</pre>
+ </blockquote>
+ <p> <i>--end example</i>]</p>
</blockquote>
<pre>path <a name="path-extension">extension</a>(const path& p) const;</pre>
<blockquote>
@@ -973,16 +985,19 @@
the substring of <code>p.filename()</code> starting at the rightmost dot
and ending at the path's end. Otherwise, returns an empty <code>path</code>
object. </p>
- <p>[<i>Example:</i> <code>std::cout << path("/foo/bar.txt").extension();</code>
- outputs "<code>.txt</code>" (without the quotes). <i>--end example</i>]</p>
+ <p><i>Remarks:</i> Implementations are permitted but not required to define additional
+ behavior for file systems which append additional elements to extensions, such
+ as alternate data streams or partitioned dataset names.</p>
+ <p>[<i>Example:</i></p>
+ <blockquote>
+ <pre><code>std::cout << path("/foo/bar.txt").extension(); //</code> outputs "<code>.txt</code>" (without the quotes)</pre>
+ </blockquote>
+ <p> <i>--end example</i>]</p>
<p>[<i>Note:<b> </b></i>The dot is included in the return value so that
it is possible to distinguish between no extension and an empty extension. See
<a href="http://permalink.gmane.org/gmane.comp.lib.boost.devel/199744">
http://permalink.gmane.org/gmane.comp.lib.boost.devel/199744> for more
extensive rationale. <i>-- end note</i>]</p>
- <p>Implementations are permitted but not required to define additional
- behavior for file systems which append additional elements to extensions, such
- as alternate data streams or partitioned dataset names.</p>
</blockquote>
<h3> <a name="path-query"> <code><font size="4">path</font></code> query</a></h3>
<pre>bool <a name="path-empty">empty</a>() const;</pre>
@@ -3144,7 +3159,7 @@
<p>Distributed under the Boost Software License, Version 1.0. See
<a href="http://www.boost.org/LICENSE_1_0.txt">www.boost.org/LICENSE_1_0.txt</a></p>
<p>Revised
-<!--webbot bot="Timestamp" S-Type="EDITED" S-Format="%d %B %Y" startspan -->22 February 2010<!--webbot bot="Timestamp" endspan i-checksum="40543" --></p>
+<!--webbot bot="Timestamp" S-Type="EDITED" S-Format="%d %B %Y" startspan -->23 February 2010<!--webbot bot="Timestamp" endspan i-checksum="40545" --></p>
</body>
Modified: sandbox/filesystem-v3/libs/filesystem/doc/tutorial.html
==============================================================================
--- sandbox/filesystem-v3/libs/filesystem/doc/tutorial.html (original)
+++ sandbox/filesystem-v3/libs/filesystem/doc/tutorial.html 2010-03-02 15:44:23 EST (Tue, 02 Mar 2010)
@@ -41,9 +41,11 @@
<a href="#Preliminaries">Preliminaries</a><br>
<a href="#Reporting-size">Reporting the size of a file - (tut1.cpp)</a><br>
<a href="#Using-status-queries">Using status queries to determine file existence and type - (tut2.cpp)</a><br>
- Directory iteration - (tut3.cpp)<br>
+ <a href="#Directory-iteration">Directory iteration plus catching
+ exceptions - (tut3.cpp)</a><br>
<a href="#Using-path-decomposition">Using path decomposition, plus sorting results - (tut4.cpp)</a><br>
- Class path: Constructors - (tut5.cpp)<br>
+ <a href="#Class-path-Constructors">Class path: Constructors, including
+ Unicode - (tut5.cpp)</a><br>
<a href="#Class-path-formats">Class path: Generic format vs. Native format</a><br>
<a href="#Class path-iterators-etc">Class path: Iterators, observers, composition, decomposition, and query - (path_info.cpp)</a><br>
<a href="#Error-reporting">Error reporting</a><br>
@@ -142,7 +144,7 @@
std::cout << "Usage: tut1 path\n";
return 1;
}
- std::cout << argv[1] << ": " << file_size(argv[1]) << '\n';
+ std::cout << argv[1] << " " << file_size(argv[1]) << '\n';
return 0;
}</pre>
</blockquote>
@@ -174,16 +176,16 @@
<tr>
<td width="50%" style="font-size: 10pt" valign="top">
<pre>$ ./tut1 tut1.cpp
-tut1.cpp: 570</pre>
+tut1.cpp 569</pre>
<pre>$ ls -l tut1.cpp
--rwxrwxrwx 1 root root 570 2010-02-01 07:31 tut1.cpp</pre>
+-rwxrwxrwx 1 root root 569 2010-02-01 07:31 tut1.cpp</pre>
</td>
<td style="font-size: 10pt" valign="top">
<pre>>tut1 tut1.cpp
-tut1.cpp: 593
+tut1.cpp 592
>dir tut1.cpp
...
-01/30/2010 10:47 AM 593 tut1.cpp
+01/30/2010 10:47 AM 592 tut1.cpp
...</pre>
</td>
</tr>
@@ -270,21 +272,19 @@
{
<a href="reference.html#class-path">path</a> p (argv[1]); // p reads clearer than argv[1] in the following code
- cout << p << ": "; // utilize the path narrow stream inserter
-
if (exists(p)) // does p actually exist?
{
if (is_regular_file(p)) // is p a regular file?
- cout << file_size(p) << '\n';
+ cout << p << " size is " << file_size(p) << '\n';
else if (is_directory(p)) // is p a directory?
- cout << "is a directory\n";
+ cout << p << "is a directory\n";
else
- cout << "exists, but is neither a regular file nor a directory\n";
+ cout << p << "exists, but is neither a regular file nor a directory\n";
}
else
- cout << "does not exist\n";
+ cout << p << "does not exist\n";
return 0;
}</pre>
@@ -303,30 +303,65 @@
<tr>
<td width="50%" style="font-size: 10pt" valign="top">
<pre>$ ./tut2 tut2.cpp
-tut2.cpp: 1037
+tut2 size is cpp 1037
$ ./tut2 foo
-foo: does not exist
+foo does not exist
$ ./tut2 .
-.: is a directory</pre>
+. is a directory</pre>
</td>
<td style="font-size: 10pt" valign="top">
<pre>>tut2 tut2.cpp
-tut2.cpp: 1079
+tut2.cpp size is 1079
>tut2 foo
-foo: does not exist
+foo does not exist
>tut2 .
-.: is a directory</pre>
+. is a directory</pre>
</td>
</tr>
</table>
-<p>Although tut2 works OK, the output is less than
-satisfactory for a directory since we'd typically like to see the directory's contents. Move
-on to <code>tut3.cpp</code> to see how to iterate over directories.</p>
+<p>Although tut2 works OK in these tests, the output is less than satisfactory
+for a directory. We'd typically like to see a list of the directory's contents. In <code>tut3.cpp</code>
+we will see how to iterate over directories.</p>
-<h2><a name="Directory-iteration">Directory iteration</a> - (tut3.cpp)</h2>
+<p>But first, let's try one more test:</p>
+
+ <table align="center" border="1" cellpadding="5" cellspacing="0" style="border-collapse: collapse" bordercolor="#111111" bgcolor="#D7EEFF" width="90%">
+ <tr>
+ <td align="center" width="50%" style="font-size: 10pt"><i><b>Ubuntu Linux </b></i></td>
+ <td align="center" style="font-size: 10pt"><i><b>Microsoft Windows</b></i></td>
+ </tr>
+ <tr>
+ <td width="50%" style="font-size: 10pt" valign="top">
+ <pre>$ ls /home/jane/foo
+ls: cannot access /home/jane/foo: Permission denied
+$ ./tut2 /home/jane/foo
+terminate called after throwing an instance of 'boost::exception_detail::
+clone_impl<boost::exception_detail::error_info_injector<boost::
+filesystem::filesystem_error> >'
+ what(): boost::filesystem::status: Permission denied:
+ "/home/jane/foo"
+Aborted</pre>
+ </td>
+ <td style="font-size: 10pt" valign="top">
+ <pre>>dir e:\
+The device is not ready.
+>tut2 e:\</pre>
+ <p><b><i>An exception is thrown; the exact form of the response depends on
+ Windows system options.</i></b></td>
+ </tr>
+ </table>
+
+<p>On the Linux system, the test was being run from an account that did not have
+permission to access <code>/home/jane/foo</code>. On the Windows system, <code>
+e:</code> was a Compact Disc reader/writer that was not ready. End users
+shouldn't have to interpret cryptic exceptions reports, so as we move on to <code>tut3.cpp</code>
+we will increase the robustness of the code, too.</p>
+
+<h2><a name="Directory-iteration">Directory iteration</a> plus catching
+exceptions - (tut3.cpp)</h2>
<p>Boost.Filesystem's <code><a href="reference.html#directory_iterator">
directory_iterator</a></code> class is just what we need here. It follows the
@@ -341,6 +376,11 @@
directory_entry</code> object
can be used directly, but can also be passed to <code>path</code> arguments in function calls.</p>
+<p>The other need is increased robustness in the face of the many kinds of
+errors that can affect file system operations. We could do that at the level of
+each call to a Boost.Filesystem function (see <a href="#Error-reporting">Error
+reporting</a>), but it is easier to supply an overall try/catch block.</p>
+
<table align="center" border="1" cellpadding="3" cellspacing="0" style="border-collapse: collapse" bordercolor="#111111" bgcolor="#D7EEFF" width="90%">
<tr>
<td style="font-size: 10pt">
@@ -350,28 +390,34 @@
{
<a href="reference.html#class-path">path</a> p (argv[1]); // p reads clearer than argv[1] in the following code
- cout << p << ": "; // utilize the path narrow stream inserter
-
- if (exists(p)) // does p actually exist?
+ try
{
- if (is_regular_file(p)) // is p a regular file?
- cout << file_size(p) << '\n';
-
- else if (is_directory(p)) // is p a directory?
+ if (exists(p)) // does p actually exist?
{
- cout << "is a directory containing:\n";
+ if (is_regular_file(p)) // is p a regular file?
+ cout << p << " size is " << file_size(p) << '\n';
- copy(directory_iterator(p), directory_iterator(), // directory_iterator::value_type
- ostream_iterator<directory_entry>(cout, "\n")); // is directory_entry, which is
- // converted to a path by the
- // path stream inserter
- }
+ else if (is_directory(p)) // is p a directory?
+ {
+ cout << p << " is a directory containing:\n";
+ copy(directory_iterator(p), directory_iterator(), // directory_iterator::value_type
+ ostream_iterator<directory_entry>(cout, "\n")); // is directory_entry, which is
+ // converted to a path by the
+ // path stream inserter
+ }
+
+ else
+ cout << p << " exists, but is neither a regular file nor a directory\n";
+ }
else
- cout << "exists, but is neither a regular file nor a directory\n";
+ cout << p << " does not exist\n";
+ }
+
+ catch (const filesystem_error& ex)
+ {
+ cout << ex.what() << '\n';
}
- else
- cout << "does not exist\n";
return 0;
}</pre>
@@ -381,7 +427,8 @@
</table>
<p>Give <code>tut3</code> a try, passing it a path to a directory as a command line argument.
-Here is a run on a checkout of the Boost Subversion trunk:</p>
+Here is a run on a checkout of the Boost Subversion trunk, followed by a repeat
+of the test cases that caused exceptions on Linux and Windows:</p>
<table align="center" border="1" cellpadding="5" cellspacing="0" style="border-collapse: collapse" bordercolor="#111111" bgcolor="#D7EEFF" width="90%">
<tr>
@@ -391,7 +438,7 @@
<tr>
<td width="50%" style="font-size: 10pt" valign="top">
<pre>$ ./tut3 ~/boost/trunk
-/home/beman/boost/trunk: is a directory containing:
+/home/beman/boost/trunk is a directory containing:
/home/beman/boost/trunk/tools
/home/beman/boost/trunk/boost-build.jam
/home/beman/boost/trunk/dist
@@ -417,7 +464,7 @@
</td>
<td style="font-size: 10pt" valign="top">
<pre>>tut3 c:\boost\trunk
-c:\boost\trunk: is a directory containing:
+c:\boost\trunk is a directory containing:
c:\boost\trunk\.svn
c:\boost\trunk\boost
c:\boost\trunk\boost-build.jam
@@ -439,7 +486,10 @@
c:\boost\trunk\rst.css
c:\boost\trunk\status
c:\boost\trunk\tools
- c:\boost\trunk\wiki</pre>
+ c:\boost\trunk\wiki
+
+>tut3 e:\
+boost::filesystem::status: The device is not ready: "e:\"</pre>
</td>
</tr>
</table>
@@ -469,36 +519,42 @@
{
<a href="reference.html#class-path">path</a> p (argv[1]); // p reads clearer than argv[1] in the following code
- cout << p << ": "; // utilize the path narrow stream inserter
-
- if (exists(p)) // does p actually exist?
+ try
{
- if (is_regular_file(p)) // is p a regular file?
- cout << file_size(p) << '\n';
-
- else if (is_directory(p)) // is p a directory?
+ if (exists(p)) // does p actually exist?
{
- cout << "is a directory containing:\n";
+ if (is_regular_file(p)) // is p a regular file?
+ cout << p << " size is " << file_size(p) << '\n';
- typedef vector<path> vec; // store paths,
- vec v; // so we can sort them later
+ else if (is_directory(p)) // is p a directory?
+ {
+ cout << p << " is a directory containing:\n";
- copy(directory_iterator(p), directory_iterator(), back_inserter(v));
+ typedef vector<path> vec; // store paths,
+ vec v; // so we can sort them later
- sort(v.begin(), v.end()); // sort, since directory iteration
- // is not ordered on some file systems
+ copy(directory_iterator(p), directory_iterator(), back_inserter(v));
- for (vec::const_iterator it (v.begin()); it != v.end(); ++it)
- {
- cout << " " << *it << '\n';
+ sort(v.begin(), v.end()); // sort, since directory iteration
+ // is not ordered on some file systems
+
+ for (vec::const_iterator it (v.begin()); it != v.end(); ++it)
+ {
+ cout << " " << *it << '\n';
+ }
}
- }
+ else
+ cout << p << " exists, but is neither a regular file nor a directory\n";
+ }
else
- cout << "exists, but is neither a regular file nor a directory\n";
+ cout << p << " does not exist\n";
+ }
+
+ catch (const filesystem_error& ex)
+ {
+ cout << ex.what() << '\n';
}
- else
- cout << "does not exist\n";
return 0;
}</pre>
@@ -539,7 +595,7 @@
<tr>
<td width="50%" style="font-size: 10pt">
<pre>$ ./tut4 ~/boost/trunk
-/home/beman/boost/trunk: is a directory containing:
+/home/beman/boost/trunk is a directory containing:
.svn
CMakeLists.txt
INSTALL
@@ -564,7 +620,7 @@
</td>
<td style="font-size: 10pt">
<pre>C:\v3d>tut4 c:\boost\trunk
-c:\boost\trunk: is a directory containing:
+c:\boost\trunk is a directory containing:
.svn
CMakeLists.txt
INSTALL
@@ -598,7 +654,8 @@
<hr>
-<h2> <a name="Class-path-Constructors">Class path: Constructors</a> - (tut5.cpp)</h2>
+<h2> <a name="Class-path-Constructors">Class path: Constructors</a>,
+including Unicode - (tut5.cpp)</h2>
<p>Traditional C interfaces pass paths as <code>const char*</code> arguments.
C++ interfaces may add <code>const std::string&</code> overloads, but adding
@@ -1092,7 +1149,7 @@
<p>Distributed under the Boost Software License, Version 1.0. See
<a href="http://www.boost.org/LICENSE_1_0.txt">www.boost.org/LICENSE_1_0.txt</a></p>
<p>Revised
-<!--webbot bot="Timestamp" S-Type="EDITED" S-Format="%d %B %Y" startspan -->22 February 2010<!--webbot bot="Timestamp" endspan i-checksum="40543" --></p>
+<!--webbot bot="Timestamp" S-Type="EDITED" S-Format="%d %B %Y" startspan -->02 March 2010<!--webbot bot="Timestamp" endspan i-checksum="27224" --></p>
</body>
Modified: sandbox/filesystem-v3/libs/filesystem/example/tut1.cpp
==============================================================================
--- sandbox/filesystem-v3/libs/filesystem/example/tut1.cpp (original)
+++ sandbox/filesystem-v3/libs/filesystem/example/tut1.cpp 2010-03-02 15:44:23 EST (Tue, 02 Mar 2010)
@@ -18,6 +18,6 @@
std::cout << "Usage: tut1 path\n";
return 1;
}
- std::cout << argv[1] << ": " << file_size(argv[1]) << '\n';
+ std::cout << argv[1] << " " << file_size(argv[1]) << '\n';
return 0;
}
Modified: sandbox/filesystem-v3/libs/filesystem/example/tut2.cpp
==============================================================================
--- sandbox/filesystem-v3/libs/filesystem/example/tut2.cpp (original)
+++ sandbox/filesystem-v3/libs/filesystem/example/tut2.cpp 2010-03-02 15:44:23 EST (Tue, 02 Mar 2010)
@@ -22,21 +22,19 @@
path p (argv[1]); // p reads clearer than argv[1] in the following code
- cout << p << ": "; // utilize the path narrow stream inserter
-
if (exists(p)) // does p actually exist?
{
if (is_regular_file(p)) // is p a regular file?
- cout << file_size(p) << '\n';
+ cout << p << " size is " << file_size(p) << '\n';
else if (is_directory(p)) // is p a directory?
- cout << "is a directory\n";
+ cout << p << " is a directory\n";
else
- cout << "exists, but is neither a regular file nor a directory\n";
+ cout << p << " exists, but is neither a regular file nor a directory\n";
}
else
- cout << "does not exist\n";
+ cout << p << " does not exist\n";
return 0;
}
Modified: sandbox/filesystem-v3/libs/filesystem/example/tut3.cpp
==============================================================================
--- sandbox/filesystem-v3/libs/filesystem/example/tut3.cpp (original)
+++ sandbox/filesystem-v3/libs/filesystem/example/tut3.cpp 2010-03-02 15:44:23 EST (Tue, 02 Mar 2010)
@@ -24,27 +24,33 @@
path p (argv[1]); // p reads clearer than argv[1] in the following code
- cout << p << ": "; // utilize the path narrow stream inserter
-
- if (exists(p)) // does p actually exist?
+ try
{
- if (is_regular_file(p)) // is p a regular file?
- cout << file_size(p) << '\n';
-
- else if (is_directory(p)) // is p a directory?
+ if (exists(p)) // does p actually exist?
{
- cout << "is a directory containing:\n";
+ if (is_regular_file(p)) // is p a regular file?
+ cout << p << " size is " << file_size(p) << '\n';
- copy(directory_iterator(p), directory_iterator(), // directory_iterator::value_type
- ostream_iterator<directory_entry>(cout, "\n")); // is directory_entry, which is
- // converted to a path by the
- // path stream inserter
+ else if (is_directory(p)) // is p a directory?
+ {
+ cout << p << " is a directory containing:\n";
+
+ copy(directory_iterator(p), directory_iterator(), // directory_iterator::value_type
+ ostream_iterator<directory_entry>(cout, "\n")); // is directory_entry, which is
+ // converted to a path by the
+ // path stream inserter
+ }
+ else
+ cout << p << " exists, but is neither a regular file nor a directory\n";
}
else
- cout << "exists, but is neither a regular file nor a directory\n";
+ cout << p << " does not exist\n";
+ }
+
+ catch (const filesystem_error& ex)
+ {
+ cout << ex.what() << '\n';
}
- else
- cout << "does not exist\n";
return 0;
}
Modified: sandbox/filesystem-v3/libs/filesystem/example/tut4.cpp
==============================================================================
--- sandbox/filesystem-v3/libs/filesystem/example/tut4.cpp (original)
+++ sandbox/filesystem-v3/libs/filesystem/example/tut4.cpp 2010-03-02 15:44:23 EST (Tue, 02 Mar 2010)
@@ -25,35 +25,41 @@
path p (argv[1]); // p reads clearer than argv[1] in the following code
- cout << p << ": "; // utilize the path narrow stream inserter
-
- if (exists(p)) // does p actually exist?
+ try
{
- if (is_regular_file(p)) // is p a regular file?
- cout << file_size(p) << '\n';
-
- else if (is_directory(p)) // is p a directory?
+ if (exists(p)) // does p actually exist?
{
- cout << "is a directory containing:\n";
+ if (is_regular_file(p)) // is p a regular file?
+ cout << p << " size is " << file_size(p) << '\n';
- typedef vector<path> vec; // store paths,
- vec v; // so we can sort them later
+ else if (is_directory(p)) // is p a directory?
+ {
+ cout << p << " is a directory containing:\n";
- copy(directory_iterator(p), directory_iterator(), back_inserter(v));
+ typedef vector<path> vec; // store paths,
+ vec v; // so we can sort them later
- sort(v.begin(), v.end()); // sort, since directory iteration
- // is not ordered on some file systems
+ copy(directory_iterator(p), directory_iterator(), back_inserter(v));
- for (vec::const_iterator it(v.begin()), it_end(v.end()); it != it_end; ++it)
- {
- cout << " " << *it << '\n';
+ sort(v.begin(), v.end()); // sort, since directory iteration
+ // is not ordered on some file systems
+
+ for (vec::const_iterator it(v.begin()), it_end(v.end()); it != it_end; ++it)
+ {
+ cout << " " << *it << '\n';
+ }
}
+ else
+ cout << p << " exists, but is neither a regular file nor a directory\n";
}
else
- cout << "exists, but is neither a regular file nor a directory\n";
+ cout << p << " does not exist\n";
+ }
+
+ catch (const filesystem_error& ex)
+ {
+ cout << ex.what() << '\n';
}
- else
- cout << "does not exist\n";
return 0;
}
Boost-Commit list run by bdawes at acm.org, david.abrahams at rcn.com, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk