2
0
mirror of https://github.com/boostorg/python.git synced 2026-01-26 06:42:27 +00:00

More tweaks (tutorial)

[SVN r15826]
This commit is contained in:
Joel de Guzman
2002-10-09 14:31:39 +00:00
parent 8a9a3a00bd
commit 8a94c597a0
8 changed files with 76 additions and 42 deletions

View File

@@ -36,22 +36,26 @@ building Boost.Python, check out: <a href="../../building.html">
building.html</a>.
After this brief <i>bjam</i> tutorial, we should have built two DLLs:</p>
<ul><li>boost_python.dll</li><li>hello.pyd</li></ul><p>
This assumes of course that we are running on Windows.</p>
if you are on Windows, and</p>
<ul><li>libboost_python.so</li><li>hello.so</li></ul><p>
if you are on Unix.</p>
<p>
The tutorial example can be found in the directory:
<tt>/libs/python/example/tutorial</tt>. There, you can find:</p>
<tt>libs/python/example/tutorial</tt>. There, you can find:</p>
<ul><li>hello.cpp</li><li>Jamfile</li></ul><p>
The <tt>hello.cpp</tt> file is our C++ hello world example. The <tt>Jamfile</tt> is a
minimalist <i>bjam</i> script that builds the DLLs for us.</p>
<p>
Before anything else, you should have the bjam executable in your boost
directory. Pre-built Boost.Jam executables are available for some
directory. Pre-built Boost.Jam executables are available for most
platforms. For example, a pre-built Microsoft Windows bjam executable can
be downloaded <a href="http://boost.sourceforge.net/jam-executables/bin.ntx86/bjam.zip">
here</a>.
The complete list of bjam pre-built executables can be found <a href="../../../../../tools/build/index.html#Jam">
here</a>.</p>
<a name="lets_jam_"></a><h2>Lets Jam!</h2><p>
<img src="theme/jam.png"></img></p>
<p>
Here is our minimalist Jamfile:</p>
<code><pre>
subproject libs/python/example/tutorial ;
@@ -99,8 +103,9 @@ Python modules. Example:</p>
</span></pre></code>
<p>
The above assumes that the Python installation is in <tt>c:/dev/tools/python</tt>
and that we are using Python version 2.2. Be sure not to include a third
number, e.g. <b>not</b> &quot;2.2.1&quot;, even if that's the version you have.</p>
and that we are using Python version 2.2. You'll have to tweak this path
appropriately. <img src="theme/note.gif"></img> Be sure not to include a third number, e.g. <b>not</b> &quot;2.2.1&quot;,
even if that's the version you have.</p>
<p>
Now we are ready... Be sure to <tt>cd</tt> to <tt>libs/python/example/tutorial</tt>
where the tutorial <tt>&quot;hello.cpp&quot;</tt> and the <tt>&quot;Jamfile&quot;</tt> is situated.</p>
@@ -139,6 +144,10 @@ And so on... Finally:</p>
</pre></code><p>
If all is well, you should now have:</p>
<ul><li>boost_python.dll</li><li>hello.pyd</li></ul><p>
if you are on Windows, and</p>
<ul><li>libboost_python.so</li><li>hello.so</li></ul><p>
if you are on Unix.</p>
<p>
<tt>boost_python.dll</tt> can be found somewhere in <tt>libs\python\build\bin</tt>
while <tt>hello.pyd</tt> can be found somewhere in
<tt>libs\python\example\tutorial\bin</tt>. After a successful build, you can just

View File

@@ -142,7 +142,7 @@ or more policies can be composed by chaining. Here's the general syntax:</p>
</span></pre></code>
<p>
Here is the list of predefined call policies. A complete reference detailing
these can be found <a href="../../v2/CallPolicies.html">
these can be found <a href="../../v2/reference.html#models_of_call_policies">
here</a>.</p>
<ul><li><b>with_custodian_and_ward</b><br> Ties lifetimes of the arguments</li><li><b>with_custodian_and_ward_postcall</b><br> Ties lifetimes of the arguments and results</li><li><b>return_internal_reference</b><br> Ties lifetime of one argument to that of result</li><li><b>return_value_policy&lt;T&gt; with T one of:</b><br></li><li><b>reference_existing_object</b><br>naïve (dangerous) approach</li><li><b>copy_const_reference</b><br>Boost.Python v1 approach</li><li><b>copy_non_const_reference</b><br></li><li><b>manage_new_object</b><br> Adopt a pointer and hold the instance</li></ul><table width="80%" border="0" align="center">
<tr>

View File

@@ -56,12 +56,11 @@ Then, in Python:</p>
Note that <tt>name</tt> is exposed as <b>read-only</b> while <tt>value</tt> is exposed
as <b>read-write</b>.</p>
<code><pre>
<span class=special>&gt;&gt;&gt; </span><span class=identifier>x</span><span class=special>.</span><span class=identifier>name </span><span class=special>= </span><span class=literal>'e' </span>#<span class=identifier>can</span><span class=literal>'t change name
&gt;&gt;&gt; x.name = 'e' # can't change name
Traceback (most recent call last):
File &quot;&lt;stdin&gt;&quot;, line 1, in ?
AttributeError: can'</span><span class=identifier>t </span><span class=identifier>set </span><span class=identifier>attribute
</span></pre></code>
<table border="0">
AttributeError: can't set attribute
</pre></code><table border="0">
<tr>
<td width="30"><a href="../index.html"><img src="theme/u_arr.gif" border="0"></a></td>
<td width="30"><a href="constructors.html"><img src="theme/l_arr.gif" border="0"></a></td>

View File

@@ -92,15 +92,16 @@ polymorphically <i>from</i> <b>C++</b>. </td>
<p>
Wrapping <tt>Base</tt> and the free function <tt>call_f</tt>:</p>
<code><pre>
<span class=identifier>class_</span><span class=special>&lt;</span><span class=identifier>Base</span><span class=special>, </span><span class=identifier>BaseWrap</span><span class=special>, </span><span class=identifier>noncopyable</span><span class=special>&gt;(</span><span class=string>&quot;Base&quot;</span><span class=special>, </span><span class=identifier>no_init</span><span class=special>)
<span class=identifier>class_</span><span class=special>&lt;</span><span class=identifier>Base</span><span class=special>, </span><span class=identifier>BaseWrap</span><span class=special>, </span><span class=identifier>boost</span><span class=special>::</span><span class=identifier>noncopyable</span><span class=special>&gt;(</span><span class=string>&quot;Base&quot;</span><span class=special>, </span><span class=identifier>no_init</span><span class=special>)
</span><span class=special>;
</span><span class=identifier>def</span><span class=special>(</span><span class=string>&quot;call_f&quot;</span><span class=special>, </span><span class=identifier>call_f</span><span class=special>);
</span></pre></code>
<p>
Notice that we parameterized the <tt>class_</tt> template with <tt>BaseWrap</tt> as the
second parameter. What is <tt>noncopyable</tt>? Without it, the library will try
to instantiate a copy constructor for returning Base objects from
functions.</p>
to create code for converting Base return values of wrapped functions to
Python. To do that, it needs Base's copy constructor... which isn't
available, since Base is an abstract class.</p>
<p>
In Python, let us try to instantiate our <tt>Base</tt> class:</p>
<code><pre>

View File

@@ -64,7 +64,7 @@ expose instead.</p>
<p>
<tt>init&lt;std::string&gt;()</tt> exposes the constructor taking in a
<tt>std::string</tt> (in Python, constructors are spelled
&quot;<tt>__init__(...)</tt>&quot;).</p>
&quot;<tt>&quot;__init__&quot;</tt>&quot;).</p>
<p>
We can expose additional constructors by passing more <tt>init&lt;...&gt;</tt>s to
the <tt>def()</tt> member function. Say for example we have another World

View File

@@ -70,18 +70,21 @@ member functions.</p>
<p>
Demonstrates that you can write the C++ equivalent of <tt>&quot;format&quot; % x,y,z</tt>
in Python, which is useful since there's no easy way to do that in std C++.</p>
<table width="80%" border="0" align="center">
<tr>
<td class="note_box">
<img src="theme/alert.gif"></img> Beware the common pitfall of
forgetting that the constructors of most of Python's mutable types
make copies, just as in Python.<br><br>
<tt>dict d(x.attr(&quot;__dict__&quot;)); # makes a copy of x's dict<br>
d['whatever'] = 3; # modifies a copy of x.__dict__ (not the original)<br></tt>
</td>
</tr>
</table>
<p>
<img src="theme/alert.gif"></img> <b>Beware</b> the common pitfall of forgetting that the constructors
of most of Python's mutable types make copies, just as in Python.</p>
<p>
Python:</p>
<code><pre>
<span class=special>&gt;&gt;&gt; </span><span class=identifier>d </span><span class=special>= </span><span class=identifier>dict</span><span class=special>(</span><span class=identifier>x</span><span class=special>.</span><span class=identifier>__dict__</span><span class=special>) </span>#<span class=identifier>copies </span><span class=identifier>x</span><span class=special>.</span><span class=identifier>__dict__
</span><span class=special>&gt;&gt;&gt; </span><span class=identifier>d</span><span class=special>[</span><span class=literal>'whatever'</span><span class=special>] </span>#<span class=identifier>modifies </span><span class=identifier>the </span><span class=identifier>copy
</span></pre></code>
<p>
C++:</p>
<code><pre>
<span class=identifier>dict </span><span class=identifier>d</span><span class=special>(</span><span class=identifier>x</span><span class=special>.</span><span class=identifier>attr</span><span class=special>(</span><span class=string>&quot;__dict__&quot;</span><span class=special>)); </span>#<span class=identifier>copies </span><span class=identifier>x</span><span class=special>.</span><span class=identifier>__dict__
</span><span class=identifier>d</span><span class=special>[</span><span class=literal>'whatever'</span><span class=special>] </span><span class=special>= </span><span class=number>3</span><span class=special>; </span>#<span class=identifier>modifies </span><span class=identifier>the </span><span class=identifier>copy
</span></pre></code>
<a name="class__lt_t_gt__as_objects"></a><h2>class_&lt;T&gt; as objects</h2><p>
Due to the dynamic nature of Boost.Python objects, any <tt>class_&lt;T&gt;</tt> may
also be one of these types! The following code snippet wraps the class

View File

@@ -65,10 +65,15 @@ After this brief ['bjam] tutorial, we should have built two DLLs:
* boost_python.dll
* hello.pyd
This assumes of course that we are running on Windows.
if you are on Windows, and
* libboost_python.so
* hello.so
if you are on Unix.
The tutorial example can be found in the directory:
[^/libs/python/example/tutorial]. There, you can find:
[^libs/python/example/tutorial]. There, you can find:
* hello.cpp
* Jamfile
@@ -77,12 +82,13 @@ The [^hello.cpp] file is our C++ hello world example. The [^Jamfile] is a
minimalist ['bjam] script that builds the DLLs for us.
Before anything else, you should have the bjam executable in your boost
directory. Pre-built Boost.Jam executables are available for some
directory. Pre-built Boost.Jam executables are available for most
platforms. For example, a pre-built Microsoft Windows bjam executable can
be downloaded [@http://boost.sourceforge.net/jam-executables/bin.ntx86/bjam.zip here].
The complete list of bjam pre-built executables can be found [@../../../../../tools/build/index.html#Jam here].
[h2 Lets Jam!]
[$theme/jam.png]
Here is our minimalist Jamfile:
@@ -141,8 +147,9 @@ Python modules. Example:
set PYTHON_VERSION=2.2
The above assumes that the Python installation is in [^c:/dev/tools/python]
and that we are using Python version 2.2. Be sure not to include a third
number, e.g. [*not] "2.2.1", even if that's the version you have.
and that we are using Python version 2.2. You'll have to tweak this path
appropriately. __note__ Be sure not to include a third number, e.g. [*not] "2.2.1",
even if that's the version you have.
Now we are ready... Be sure to [^cd] to [^libs/python/example/tutorial]
where the tutorial [^"hello.cpp"] and the [^"Jamfile"] is situated.
@@ -186,6 +193,13 @@ If all is well, you should now have:
* boost_python.dll
* hello.pyd
if you are on Windows, and
* libboost_python.so
* hello.so
if you are on Unix.
[^boost_python.dll] can be found somewhere in [^libs\python\build\bin]
while [^hello.pyd] can be found somewhere in
[^libs\python\example\tutorial\bin]. After a successful build, you can just
@@ -276,7 +290,7 @@ expose instead.
[^init<std::string>()] exposes the constructor taking in a
[^std::string] (in Python, constructors are spelled
"[^__init__(...)]").
"[^"__init__"]").
We can expose additional constructors by passing more [^init<...>]s to
the [^def()] member function. Say for example we have another World
@@ -326,10 +340,12 @@ Then, in Python:
Note that [^name] is exposed as [*read-only] while [^value] is exposed
as [*read-write].
[pre
>>> x.name = 'e' # can't change name
Traceback (most recent call last):
File "<stdin>", line 1, in ?
AttributeError: can't set attribute
]
[page:1 Class Properties]
@@ -482,14 +498,15 @@ polymorphically ['from] [*C++].]
Wrapping [^Base] and the free function [^call_f]:
class_<Base, BaseWrap, noncopyable>("Base", no_init)
class_<Base, BaseWrap, boost::noncopyable>("Base", no_init)
;
def("call_f", call_f);
Notice that we parameterized the [^class_] template with [^BaseWrap] as the
second parameter. What is [^noncopyable]? Without it, the library will try
to instantiate a copy constructor for returning Base objects from
functions.
to create code for converting Base return values of wrapped functions to
Python. To do that, it needs Base's copy constructor... which isn't
available, since Base is an abstract class.
In Python, let us try to instantiate our [^Base] class:
@@ -820,7 +837,7 @@ or more policies can be composed by chaining. Here's the general syntax:
policy3<args...> > >
Here is the list of predefined call policies. A complete reference detailing
these can be found [@../../v2/CallPolicies.html here].
these can be found [@../../v2/reference.html#models_of_call_policies here].
* [*with_custodian_and_ward][br] Ties lifetimes of the arguments
* [*with_custodian_and_ward_postcall][br] Ties lifetimes of the arguments and results
@@ -1007,13 +1024,18 @@ member functions.
Demonstrates that you can write the C++ equivalent of [^"format" % x,y,z]
in Python, which is useful since there's no easy way to do that in std C++.
[blurb __alert__ Beware the common pitfall of
forgetting that the constructors of most of Python's mutable types
make copies, just as in Python.[br][br]
__alert__ [*Beware] the common pitfall of forgetting that the constructors
of most of Python's mutable types make copies, just as in Python.
[^dict d(x.attr("__dict__")); # makes a copy of x's dict[br]
'''d['whatever']''' = 3; # modifies a copy of x.__dict__ (not the original)[br]]
]
Python:
>>> d = dict(x.__dict__) # copies x.__dict__
>>> d['whatever'] # modifies the copy
C++:
dict d(x.attr("__dict__")); # copies x.__dict__
d['whatever'] = 3; # modifies the copy
[h2 class_<T> as objects]

BIN
doc/tutorial/doc/theme/jam.png vendored Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.8 KiB