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

Compare commits

..

145 Commits

Author SHA1 Message Date
Beman Dawes
950ed457cd Branch at revision 46530
[SVN r46531]
2008-06-19 18:57:10 +00:00
Markus Schöpflin
b01e0e6b9c Added missing ostream header file.
[SVN r46115]
2008-06-04 15:11:05 +00:00
Ralf W. Grosse-Kunstleve
b0a9b11c9c Projects using Boost.Python: PolyBoRi (text provided by Michael Brickenstein)
[SVN r45920]
2008-05-29 20:04:19 +00:00
Ralf W. Grosse-Kunstleve
304277b806 See Python C++-SIG thread: "object.attr(object& attrname) proposal"
Started 2008-05-25 by hohehohe2@gmail.com.

Excerpts:

If char const* is passed to objecjt.attr(), it uses
PyObject_GetAttrStrng() or PyObject_SetAttrStrng().  If object is
passed to objecjt.attr(), it takes the object as a Python string
object and uses PyObject_GetAttr() or PyObject_SetAttr().

If attr() behaves like this, it can be useful when there are lots
of objects which you know have the same attribute name. You can save
time by first making a boost::python::object and passing it to every
object's attr() inside a loop.

I just made a bit of modification to boost:python locally and did a
quick test, like

test 1:
  for(int i = 0; i < n; ++i)
  {
    omain.attr(attrname) = 444; //attrname is a char const*
  }

test 2:
  for(int i = 0; i < n; ++i)
  {
    object o = omain.attr(attrname); //attrname is a char const*
  }

test 3:
  for(int i = 0; i < n; ++i)
  {
    omain.attr(oaaaa) = 444; //oaaaa is boost::python::object that represents a string
  }

test 4:
  for(int i = 0; i < n; ++i)
  {
    object o = omain.attr(oaaaa); //oaaaa is boost::python::object that represents a string
  }

and it reasonably reflected the difference between PyObject_*Attr() and PyObject_*AttrString.

test 1 :2783ms
test 2 :2357ms
test 3 :1882ms
test 4 :1267ms

test5: PyObject_SetAttrString(po_main, "aaaa", po_num444);
test6: Py_DECREF(PyObject_GetAttrString(po_main, "aaaa"));
test7: PyObject_SetAttr(po_main, po_aaaa, po_num444);
test8: Py_DECREF(PyObject_GetAttr(po_main, po_aaaa));
(po_ prefixed variables are PyObject*),

all inside each for loop, and the results were

test 5 :2410ms
test 6 :2277ms
test 7 :1629ms
test 8 :1094ms

It's boost 1.35.0, Python 2.5 on linux(gcc4.1.2).
I also did the same test on windows(vs8) and the tendency was not
so different.


[SVN r45918]
2008-05-29 19:48:55 +00:00
Ralf W. Grosse-Kunstleve
a334649b0c braces added to resolve g++ 4.3.0 warning
[SVN r45359]
2008-05-14 19:38:08 +00:00
Daniel James
79b7f88df6 Quote href values - our tools don't support unquoted values.
[SVN r45283]
2008-05-11 13:49:20 +00:00
Daniel James
a33ed032c6 Merge in documentation fixes. Apart from the change to optional's documenation
Jamfile, which I included by mistake.

Fixes #1659, #1661, #1684, #1685, 1687, #1690, #1801

I wrote about this at:

http://lists.boost.org/Archives/boost/2008/04/136405.php

Merged revisions 44585-44806 via svnmerge from 
https://svn.boost.org/svn/boost/branches/doc

........
  r44585 | danieljames | 2008-04-19 16:25:27 +0100 (Sat, 19 Apr 2008) | 2 lines
  
  Fix broken link to vacpp in bjam docs. Refs #1512
........
  r44586 | danieljames | 2008-04-19 16:27:36 +0100 (Sat, 19 Apr 2008) | 2 lines
  
  Fix broken link to bcpp in bjam docs. Refs #1513
........
  r44587 | danieljames | 2008-04-19 16:33:58 +0100 (Sat, 19 Apr 2008) | 2 lines
  
  DateTime documentation - Fix a link to the serialization library. Refs #1659
........
  r44588 | danieljames | 2008-04-19 16:35:36 +0100 (Sat, 19 Apr 2008) | 2 lines
  
  Fix some links in interprocess & intrusive. Refs #1661
........
  r44589 | danieljames | 2008-04-19 16:37:39 +0100 (Sat, 19 Apr 2008) | 2 lines
  
  Fix some links in the python docs. Refs #1684.
........
  r44590 | danieljames | 2008-04-19 16:38:29 +0100 (Sat, 19 Apr 2008) | 2 lines
  
  Work around a quickbook bug which is affecting the python docs. Refs #1684.
........
  r44591 | danieljames | 2008-04-19 16:39:34 +0100 (Sat, 19 Apr 2008) | 2 lines
  
  Fix a broken link in the numeric conversion docs. Refs #1685
........
  r44592 | danieljames | 2008-04-19 16:40:45 +0100 (Sat, 19 Apr 2008) | 2 lines
  
  Fix some links in the optional docs. Refs #1687
........
  r44593 | danieljames | 2008-04-19 16:42:09 +0100 (Sat, 19 Apr 2008) | 2 lines
  
  Fix link to the hash documentation from bimap. Refs #1690
........
  r44599 | danieljames | 2008-04-19 18:07:33 +0100 (Sat, 19 Apr 2008) | 2 lines
  
  Fix a typo in the format library. Refs #1801
........
  r44600 | danieljames | 2008-04-19 19:20:59 +0100 (Sat, 19 Apr 2008) | 1 line
  
  Initialise svnmerge.
........
  r44641 | danieljames | 2008-04-20 18:59:47 +0100 (Sun, 20 Apr 2008) | 2 lines
  
  Fix the lincense url in shared container iterator documentation.
........
  r44642 | danieljames | 2008-04-20 19:00:00 +0100 (Sun, 20 Apr 2008) | 2 lines
  
  Fix image link in the mpi documentation.
........
  r44643 | danieljames | 2008-04-20 19:00:11 +0100 (Sun, 20 Apr 2008) | 2 lines
  
  Fix a typo in the spirit docs.
........
  r44644 | danieljames | 2008-04-20 19:00:23 +0100 (Sun, 20 Apr 2008) | 2 lines
  
  Escape the slash so that quickbook doesn't think it the start of an italic section, and mess up the link. Refs #1844
........
  r44647 | danieljames | 2008-04-20 19:39:47 +0100 (Sun, 20 Apr 2008) | 2 lines
  
  Fix another typo in spirit docs.
........


[SVN r44807]
2008-04-27 07:39:49 +00:00
Joel de Guzman
b316819925 Andreas indexing suite patch
[SVN r44450]
2008-04-16 03:07:11 +00:00
Joel de Guzman
52245de2e5 Andreas patch
[SVN r44449]
2008-04-16 03:07:06 +00:00
Ralf W. Grosse-Kunstleve
2f1f79ce87 bogus VC8 warning C4180 disabled
[SVN r44041]
2008-04-04 18:57:27 +00:00
Beman Dawes
863bff9072 Remove per email from Dave
[SVN r43901]
2008-03-28 02:11:13 +00:00
Dave Abrahams
2213cf98c6 Work around vc9 bugs
[SVN r43845]
2008-03-24 18:27:22 +00:00
Ralf W. Grosse-Kunstleve
2dba3148ce map std::invalid_argument -> Python ValueError
[SVN r43546]
2008-03-09 04:30:13 +00:00
Daniel James
48aa6ab9a9 Fix incorrect links to copyright of the form 'http:#www.boost.org
[SVN r43423]
2008-02-27 19:22:01 +00:00
Daniel James
6ba5067e0b Point links to the pages that used to be in 'more' to the site.
[SVN r43210]
2008-02-10 15:02:17 +00:00
Daniel James
60f4f5e54c Link to people pages on the website, as they've been removed from the download.
[SVN r43209]
2008-02-10 14:56:22 +00:00
Eric Niebler
7ee9cf679b stl_iterator does better error handling
[SVN r42836]
2008-01-17 22:47:54 +00:00
Ralf W. Grosse-Kunstleve
03a72363a4 undo revision 41404; see http://gcc.gnu.org/bugzilla/show_bug.cgi?id=34238
[SVN r41986]
2007-12-12 05:39:45 +00:00
Jürgen Hunold
38cc1a0c15 Add cosmetic virtual detructors to silence compile warnings.
[SVN r41650]
2007-12-03 18:51:26 +00:00
Jürgen Hunold
ff44521920 Silence unused paramter warning in release mode.
[SVN r41649]
2007-12-03 18:47:17 +00:00
Jürgen Hunold
0ac7e3f858 Revert revisions 41544 and 41549.
See http://lists.boost.org/Archives/boost/2007/12/131116.php for details.


[SVN r41577]
2007-12-02 11:51:08 +00:00
Jürgen Hunold
5cbb539ec5 Remove unused paramters.
Add -Wextra to gcc flags to enable more warnings.


[SVN r41550]
2007-12-01 20:26:37 +00:00
Jürgen Hunold
40e4940877 Silence compiler by adding cosmetic virtual destructors.
[SVN r41549]
2007-12-01 20:24:51 +00:00
Jürgen Hunold
ab0911cf53 Silence compiler by adding cosmetic virtual destructors.
[SVN r41544]
2007-12-01 19:27:06 +00:00
Dave Abrahams
0d81eb6695 Boost.Python:
* Workarounds for many SunCC 5.9 bugs
* Suppression of many SunCC 5.9 warnings
* Improve the style of some test invocations in Jamfile


[SVN r41521]
2007-12-01 02:15:17 +00:00
Dave Abrahams
e0b535df1e Try to extend the workaround to SunPro 5.9, since we're marked as not working on 5.8
[SVN r41408]
2007-11-26 22:01:50 +00:00
Ralf W. Grosse-Kunstleve
d2517faa78 g++ 4.3.0 compatibility (4.3.0 20071125 (experimental))
[SVN r41404]
2007-11-26 20:46:28 +00:00
Beman Dawes
8cd4ff8950 Remove extra ) from prior commit
[SVN r41355]
2007-11-25 13:56:09 +00:00
Dave Abrahams
26f77691ee Attempt SunPro workaround
[SVN r41352]
2007-11-25 09:02:01 +00:00
Joel de Guzman
6e7f594027 fix for trac ticket #1450
[SVN r41164]
2007-11-17 01:51:04 +00:00
Beman Dawes
eada30f0cb Get rid of .cvsignore files
[SVN r41107]
2007-11-15 15:20:27 +00:00
Joel de Guzman
e919ffdac4 refresh docs
[SVN r41082]
2007-11-14 10:24:21 +00:00
Joel de Guzman
1cf41fd031 fix mismatch include guard
[SVN r41019]
2007-11-11 22:32:48 +00:00
Nikolay Mladenov
7b67118271 changed handle cast to downcast
[SVN r40935]
2007-11-08 16:28:44 +00:00
Nikolay Mladenov
e14c702a40 added forgotten array_object_manager_traits::get_pytype
[SVN r40889]
2007-11-07 16:06:55 +00:00
Joel de Guzman
d303ea16fc added copyright and license info for each page.
[SVN r40871]
2007-11-07 03:35:49 +00:00
Ralf W. Grosse-Kunstleve
65114d8637 reinterpret_cast -> const_cast; commented out dead code removed
[SVN r40749]
2007-11-04 18:08:28 +00:00
Joel de Guzman
597dfc586b tutorial update
[SVN r40734]
2007-11-04 00:12:29 +00:00
Dave Abrahams
6a3085ad5d Merging some of the more obvious changes from RC_1_34_0
[SVN r40714]
2007-11-03 03:25:13 +00:00
Joel de Guzman
190d0d7ea6 replacing reinterpret_cast with static_cast<PySliceObject*>(static_cast<void*>(i))
[SVN r40712]
2007-11-03 03:05:26 +00:00
Eric Niebler
8b915a15ff merge Changeset 37947
[SVN r40675]
2007-11-02 04:35:01 +00:00
Dave Abrahams
90c5c19220 Take out print statement I added for debugging purposes.
[SVN r40536]
2007-10-28 19:24:02 +00:00
Dave Abrahams
cfe6f96f69 Closes #1379, really this time. The old code would sandwich argv[1] between quotes and interpret it as a string, so backslashes in windows paths were interpreted as escape sequences.
[SVN r40535]
2007-10-28 19:22:21 +00:00
Vladimir Prus
77907c5369 Make sure every library can be installed by using
bjam stage|install

in libs/<library>/build.


[SVN r40475]
2007-10-26 09:04:25 +00:00
Rene Rivera
512b30c971 Do not refer to nonexistent target when python is not configured.
[SVN r40216]
2007-10-20 16:36:18 +00:00
Rene Rivera
f005518686 Fix build system error when Python is not configured, without preventing the BPL target from being declared. Instead the target is now unbuildable, and will be skipped when Python is not configured.
[SVN r40156]
2007-10-18 16:11:41 +00:00
Rene Rivera
274a219965 Remove BPL build conditional as it prevents normal build failures.
[SVN r39731]
2007-10-06 19:46:39 +00:00
Ralf W. Grosse-Kunstleve
abc4abf84a gcc 4.3.0 compatibility (resolves new "changes meaning" error)
[SVN r39434]
2007-09-20 23:20:45 +00:00
Nikolay Mladenov
94a3ced83a fixed cpp signature related test failure
[SVN r39372]
2007-09-18 17:51:47 +00:00
Nikolay Mladenov
7eb0c678ee epydoc friendlier formatting
[SVN r39371]
2007-09-18 17:32:06 +00:00
Nikolay Mladenov
92460adce6 tabs removes, code reformatting
[SVN r39370]
2007-09-18 17:28:23 +00:00
Nikolay Mladenov
8cfd3fb2ef epydoc friendlier formatting
[SVN r39368]
2007-09-18 17:16:31 +00:00
Nikolay Mladenov
62ef542eaf fixed problem reported by Neal Becker; added a test case
[SVN r39223]
2007-09-12 21:31:39 +00:00
Ralf W. Grosse-Kunstleve
5809078ba9 Patches by Nikolay Mladenov (nickm at sitius com): new pythonic signatures; docstring support for enums; fix unrelated Visual C++ 6 problem
[SVN r39191]
2007-09-11 16:53:50 +00:00
Vladimir Prus
04e54d670c Remove V1 Jamfiles
[SVN r38516]
2007-08-08 19:02:26 +00:00
Stefan Seefeld
dd7c0a7f3d Fix ticket #1115.
[SVN r38289]
2007-07-26 16:11:18 +00:00
Stefan Seefeld
71f54cc920 Fix ticket #1115.
[SVN r38288]
2007-07-26 14:41:41 +00:00
Ralf W. Grosse-Kunstleve
9de994c0d1 Hans Meine's extra new-line for epydoc with reST compatibility
[SVN r37906]
2007-06-06 00:00:57 +00:00
Stefan Seefeld
e9caacc428 More fixes for embedding python docs.
[SVN r37709]
2007-05-18 15:52:55 +00:00
Stefan Seefeld
5070e84f70 Enhance documentation for embedding python.
[SVN r37708]
2007-05-18 15:22:43 +00:00
Stefan Seefeld
fe23d9885f Add new eval() function.
[SVN r37560]
2007-05-02 13:11:20 +00:00
Ralf W. Grosse-Kunstleve
e7ee17b71b MIPSpro: undo Python 2.5.1 define (the define leads to many warnings)
[SVN r37502]
2007-04-25 04:45:17 +00:00
Dave Abrahams
5edb63d01c Some progress on Python build guide. Minor fixes to getting started guide.
[SVN r37418]
2007-04-11 23:35:08 +00:00
Dave Abrahams
f4b3aab7d4 Checkpoint before reorg
[SVN r37370]
2007-04-05 20:13:13 +00:00
Dave Abrahams
6af67d1a4c kill off BBv1 project archive
[SVN r37367]
2007-04-05 17:19:20 +00:00
Dave Abrahams
16d975ba5c Bringing forward BBv2/Python support and a few other things that were
obviously more up-to-date on the RC branch.

Removed the Boost.Python v1 zip archive.


[SVN r37346]
2007-04-03 17:10:53 +00:00
Dave Abrahams
4fc5cafd40 Some progress on new build/test guide.
[SVN r37333]
2007-04-02 05:24:25 +00:00
Stefan Seefeld
1b5cd10f7c Fix reference counting error.
[SVN r37312]
2007-03-28 18:12:08 +00:00
Stefan Seefeld
0f91872518 Fix import_ failure.
[SVN r37142]
2007-03-05 18:51:04 +00:00
Stefan Seefeld
dc6b2979e4 Add copyright notice.
[SVN r37132]
2007-03-02 17:16:51 +00:00
Stefan Seefeld
50034140c4 Fix boost::python::import.
[SVN r37120]
2007-03-01 15:17:29 +00:00
Dave Abrahams
08a6f35ec2 Correct testing bugs:
either changing assert(...) or BOOST_ASSERT(...) to BOOST_TEST
    (in my code only)

    or adding "return boost::report_errors();" where it was clearly
    missing (and a pure bug, in anyone's code).


[SVN r37057]
2007-02-24 22:40:59 +00:00
Dave Abrahams
67236ffbad New build instructions in progress
[SVN r36879]
2007-02-03 16:55:07 +00:00
Dave Abrahams
96ab7a80a4 Remove BBv1 for good
[SVN r36323]
2006-12-11 05:02:34 +00:00
Dave Abrahams
d8c3ff199e Remove BBv1 for good
[SVN r36321]
2006-12-11 03:35:10 +00:00
Dave Abrahams
0c4ebef579 Fix auto-link to look at the right variable.
Make boost-build.jam point at the v2 Boost.


[SVN r36318]
2006-12-11 02:54:48 +00:00
Dave Abrahams
8fe9d41b58 Cleaned out flotsam and improved comments
[SVN r36317]
2006-12-11 02:50:55 +00:00
Dave Abrahams
8a4590b2ef Enable auto-linking
[SVN r36291]
2006-12-07 17:44:05 +00:00
Ralf W. Grosse-Kunstleve
d67b040683 fixes to support pickling of enums (by Shashank Bapat)
[SVN r36256]
2006-12-03 20:43:48 +00:00
Beman Dawes
2db61657f2 Add copyright, license
[SVN r35905]
2006-11-07 19:11:57 +00:00
Dave Abrahams
6d2ee96ba3 improve error message
[SVN r35822]
2006-11-03 16:34:53 +00:00
Stefan Seefeld
a74c8e3da3 Fix symbol visibility.
[SVN r35754]
2006-10-27 21:19:47 +00:00
Ralf W. Grosse-Kunstleve
9f4d39d9fe correct trivial, obvious accident: stray line removed
[SVN r35599]
2006-10-13 22:06:17 +00:00
Dave Abrahams
31c19644ed make numpy tests portable to Darwin with older docutils
[SVN r35597]
2006-10-13 21:34:26 +00:00
Dave Abrahams
600d444136 Fix some problems with testing on old docutils installations
[SVN r35594]
2006-10-13 19:35:28 +00:00
Dave Abrahams
c3bd0fcbad Make object comparison operators return object instead of bool, to
accomodate strange beasts like numarray arrays that return arrays that
can't be used as truth values from their comparison ops.

Fix numpy test for portability with old doctest (again!)


[SVN r35572]
2006-10-12 09:07:07 +00:00
Dave Abrahams
991a7c198a Workaround vc6 bugs
[SVN r35568]
2006-10-12 06:41:55 +00:00
Dave Abrahams
9b67f0447d Suppress a couple of msvc class/struct warnings
[SVN r35567]
2006-10-12 06:41:18 +00:00
Dave Abrahams
b714f6cc23 Adjust tests to account for numarray behavior differences
[SVN r35539]
2006-10-10 22:44:09 +00:00
Dave Abrahams
479a6ba4fc Try for backward compatibility with older versions of doctest
[SVN r35535]
2006-10-10 18:12:43 +00:00
Dave Abrahams
d78836b828 Fix lots of bugs in the numeric interface and tests.
Tests:
* Coerce a result to bool to deal with Python's new Bool type
* Better reporting of mismatches in expected and received results
* Remove bogus nullary y.astype() call
* Fix all uses of trace and diagonal so they don't cause errors
* Use appropriate typecodes
* Use doctest detailed API to run just the relevant tests
* Factor out error handling from macro

API:
* Added get_module_name() function to get current numeric module
* new_(x) now returns an array instead of object
* Fixed the signatures of the factory() family of functions
* Updated docs accordingly.


[SVN r35528]
2006-10-09 04:05:25 +00:00
Dave Abrahams
7a59131d37 Fix missing #include
[SVN r35524]
2006-10-08 05:17:20 +00:00
Dave Abrahams
5ab00bc9c8 Fix long-standing misnaming of "factory" method as "array"
[SVN r35428]
2006-09-29 22:24:12 +00:00
Dave Abrahams
94500ae36d Tests and fixes for a bad interaction between wrapper<> and operators
support.  "self" arguments weren't getting unwrapped properly.


[SVN r35365]
2006-09-28 14:41:01 +00:00
Dave Abrahams
5e5d34cc36 Fixed broken links
[SVN r35329]
2006-09-26 04:23:32 +00:00
Ralf W. Grosse-Kunstleve
c6f2aa4ef2 new boost/python/ssize_t.hpp; avoids potential clash of Py_ssize_t typedef and PY_SSIZE_T_MIN/MAX macros with definitions from other libraries
[SVN r35325]
2006-09-26 00:25:07 +00:00
Dave Abrahams
c7fb2f7047 Attempt GCC-3.4.4 and 4.0.1 workarounds
[SVN r35276]
2006-09-22 15:12:04 +00:00
Vladimir Prus
afedc1cd9a Add tests
[SVN r35244]
2006-09-21 07:26:35 +00:00
Gottfried Ganßauge
070e02d7d5 Renamed from opaque_pointer_converter.html
[SVN r35242]
2006-09-21 07:07:14 +00:00
Dave Abrahams
ccc56c2a4c Apply Boost license, with permission from Prabhu Ramachandran.
[SVN r35240]
2006-09-21 03:43:59 +00:00
Dave Abrahams
e00a88ff49 Fix inspection issues
[SVN r35239]
2006-09-21 02:40:19 +00:00
Stefan Seefeld
e527bc860f Fix copyright issues.
[SVN r35236]
2006-09-20 22:30:39 +00:00
Dave Abrahams
921e306b9a Fix license/copyright
[SVN r35234]
2006-09-20 21:59:03 +00:00
Dave Abrahams
bed1d26904 Return an int, not a string, on success from
check_numeric_array_rich_slice, since that's what the tests expect.


[SVN r35184]
2006-09-18 22:21:50 +00:00
Dave Abrahams
41a342f026 vc6/7 workaround
[SVN r35164]
2006-09-18 18:25:12 +00:00
Dave Abrahams
cee8e07046 Checkin missing op_repr definition
[SVN r35153]
2006-09-18 02:59:31 +00:00
Dave Abrahams
0806e89964 More informative error messages
Better autoconfiguration


[SVN r35140]
2006-09-17 02:41:20 +00:00
Dave Abrahams
f5421ca6b2 Default to Python 2.4 in Unix builds
Applied contributed patches http://tinyurl.com/ndljr and
http://tinyurl.com/18r


[SVN r35138]
2006-09-16 18:43:53 +00:00
Ralf W. Grosse-Kunstleve
eea7697175 if __name__ == '__main__'
[SVN r35114]
2006-09-14 21:57:56 +00:00
Ralf W. Grosse-Kunstleve
777ce7b561 magic coding: iso-latin1 comment added to avoid Python SyntaxError
[SVN r35113]
2006-09-14 21:53:00 +00:00
Gottfried Ganßauge
864ece5539 cross module compatibility test for opaque
[SVN r35111]
2006-09-14 19:06:33 +00:00
Gottfried Ganßauge
2610eb9acb Type object for opaque initialized with PyType_Clear.
opaque is registered only if not another module has already registered
a conversion for that pointer type.
Doc update.


[SVN r35104]
2006-09-14 05:59:29 +00:00
Dave Abrahams
567a2c7b89 attempt unverified workaround for http://tinyurl.com/gvrgd
[SVN r35103]
2006-09-13 22:47:11 +00:00
Dave Abrahams
05070faf12 Attempt to capture better debugging info in output
[SVN r35079]
2006-09-12 23:58:40 +00:00
Dave Abrahams
ad8069314d Move definition of BOOST_PYTHON_SUPPRESS_REGISTRY_INITIALIZATION back
where it belongs.


[SVN r35076]
2006-09-12 22:37:09 +00:00
Dave Abrahams
9366c48351 add missing license/copyright info
[SVN r35068]
2006-09-11 22:08:18 +00:00
Dave Abrahams
5a14319753 SunPro workarounds
[SVN r35067]
2006-09-11 10:38:14 +00:00
Joel de Guzman
279a4f7888 Update
[SVN r35006]
2006-08-31 06:01:57 +00:00
Dave Abrahams
d3418d494c Restort BOOST_PYTHON_STATIC_LIB. We don't want to create exported symbols.
[SVN r34942]
2006-08-24 19:03:35 +00:00
Dave Abrahams
c839427246 Sun workaround
[SVN r34939]
2006-08-24 13:04:59 +00:00
Dave Abrahams
dd3a136b18 Attempted Sun workaround
[SVN r34914]
2006-08-22 11:50:35 +00:00
Dave Abrahams
48696918de Try not specifying static link, to see if it makes Darwin happy
[SVN r34871]
2006-08-11 15:50:21 +00:00
Dave Abrahams
88be35ddc2 Attempt Sun-5.8 workaround
[SVN r34864]
2006-08-11 00:47:48 +00:00
Gennaro Prota
9ee0d36a1d removed tabs (inspect tool)
[SVN r34722]
2006-07-24 22:25:35 +00:00
Gennaro Prota
f240e0bab6 removed tabs (inspect tool)
[SVN r34720]
2006-07-24 22:20:25 +00:00
Gennaro Prota
4081605e4b removed tabs (inspect tool)
[SVN r34719]
2006-07-24 22:14:15 +00:00
Gennaro Prota
f332ff2d89 minor fix: violation of min/max guidelines
[SVN r34717]
2006-07-24 22:04:05 +00:00
Vladimir Prus
ec77608840 Clarify comment
[SVN r34668]
2006-07-22 12:53:49 +00:00
Vladimir Prus
f5a69a1dab Windows fix: use <library>/pytho/python_for_extensions, not <use>, so that
we actually link to Python import lib on windows.


[SVN r34666]
2006-07-22 12:28:00 +00:00
Vladimir Prus
a1e865061c Don't link Boost.Python to python library, and don't require
<threading>multi for embedding applications.

* libs/python/build/Jamfile.v2: (boost_python): Don't link
  to /python//python. Use /python//python_for_extensions.

* libs/python/test/Jamfile.v2: Remove <threading>multi project
  requirements.
  (py-run): Link to /python//python.
  (exec): Likewise.

* tools/build/v2/tools/python.jam: (pthread): Declare.
  (init-unix): Add 'pthread' to extra-libs.
  (


[SVN r34662]
2006-07-22 07:12:10 +00:00
Ralf W. Grosse-Kunstleve
596e92404a old misunderstanding corrected (L-BFGS)
[SVN r34504]
2006-07-11 04:09:41 +00:00
Joel de Guzman
2640f5af94 new css
[SVN r34426]
2006-06-29 09:35:52 +00:00
Joel de Guzman
0605e9fdcf minor tweak
[SVN r34375]
2006-06-22 13:43:09 +00:00
Joel de Guzman
cf68da0b19 added test for vector<string>
[SVN r34374]
2006-06-22 13:33:46 +00:00
Joel de Guzman
d3c474b295 terminology tweak
[SVN r34360]
2006-06-20 14:01:12 +00:00
Joel de Guzman
c9300e07c2 added custom converter test for map indexing suite
[SVN r34359]
2006-06-20 00:33:22 +00:00
Ralf W. Grosse-Kunstleve
cab94a7bba adjustments for new MIPSpro 7.4.4
[SVN r34132]
2006-06-02 05:39:50 +00:00
Ralf W. Grosse-Kunstleve
caa9cb8268 Python 2.5 compatibility
[SVN r34017]
2006-05-18 22:41:14 +00:00
Ralf W. Grosse-Kunstleve
66ac61450e avoid Visual C++ 7.1 "resolved overload was found by argument-dependent lookup" warning
[SVN r34016]
2006-05-18 22:09:20 +00:00
Ralf W. Grosse-Kunstleve
59f81def56 Python include must appear before any system include
[SVN r34010]
2006-05-18 18:47:12 +00:00
Ralf W. Grosse-Kunstleve
92862028b7 MIPSpro 7.3.1 compatibility
[SVN r34009]
2006-05-18 18:46:26 +00:00
Ralf W. Grosse-Kunstleve
b0ba7dfc50 also exercise OVERLOADS with docstring
[SVN r34006]
2006-05-18 16:15:59 +00:00
Ralf W. Grosse-Kunstleve
fe3abeda9f much more informative pickle error messages if pickling is not enabled
[SVN r34004]
2006-05-18 15:49:41 +00:00
Markus Schöpflin
3fdfb30e33 Include python first, fixes error on Tru64/CXX.
[SVN r33454]
2006-03-23 09:38:03 +00:00
Vladimir Prus
cdcf8633bb Force multithreading for Python test.
Workaround for problem described in
http://thread.gmane.org/gmane.comp.lib.boost.devel/139601


[SVN r33434]
2006-03-22 09:53:34 +00:00
231 changed files with 1833 additions and 3441 deletions

Binary file not shown.

View File

@@ -3,9 +3,7 @@
# file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) # file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
import os ; import os ;
import indirect ;
import modules ; import modules ;
import feature ;
import python ; import python ;
@@ -14,138 +12,83 @@ if ! [ python.configured ] && ! ( --without-python in [ modules.peek : ARGV ] )
# Attempt default configuration of python # Attempt default configuration of python
import toolset : using ; import toolset : using ;
using python ; using python ;
}
if ! [ python.configured ]
if [ python.configured ] || ( --without-python in [ modules.peek : ARGV ] )
{
alias config-warning ;
}
else
{
message config-warning
: "warning: No python installation configured and autoconfiguration"
: "note: failed. See http://www.boost.org/libs/python/doc/building.html"
: "note: for configuration instructions or pass --without-python to"
: "note: suppress this message and silently skip all Boost.Python targets"
;
}
rule find-py3-version
{
local versions = [ feature.values python ] ;
local py3ver ;
for local v in $(versions)
{ {
if $(v) >= 3.0 ECHO "WARNING: No python installation configured and autoconfiguration" ;
{ ECHO " failed. See http://www.boost.org/libs/python/doc/building.html" ;
py3ver = $(v) ; ECHO " for configuration instructions or pass --without-python to" ;
} ECHO " suppress this message and silently skip all Boost.Python targets" ;
} }
return $(py3ver) ;
} }
py3-version = [ find-py3-version ] ;
project boost/python project boost/python
: source-location ../src : source-location ../src
: requirements
-<tag>@$(BOOST_JAMROOT_MODULE)%$(BOOST_JAMROOT_MODULE).tag
<tag>@$(__name__).tag
; ;
rule tag ( name : type ? : property-set )
{
local result = $(name) ;
if $(type) in STATIC_LIB SHARED_LIB IMPORT_LIB
{
if $(name) = boost_python && $(PYTHON_ID)
{
result = $(result)-$(PYTHON_ID) ;
}
}
# forward to the boost tagging rule
return [ indirect.call $(BOOST_JAMROOT_MODULE)%$(BOOST_JAMROOT_MODULE).tag
$(result) : $(type) : $(property-set) ] ;
}
rule cond ( test ? : yes * : no * ) { if $(test) { return $(yes) ; } else { return $(no) ; } } rule cond ( test ? : yes * : no * ) { if $(test) { return $(yes) ; } else { return $(no) ; } }
rule unless ( test ? : yes * : no * ) { if ! $(test) { return $(yes) ; } else { return $(no) ; } } rule unless ( test ? : yes * : no * ) { if ! $(test) { return $(yes) ; } else { return $(no) ; } }
rule lib_boost_python ( is-py3 ? ) lib boost_python
{ : # sources
numeric.cpp
list.cpp
long.cpp
dict.cpp
tuple.cpp
str.cpp
slice.cpp
lib [ cond $(is-py3) : boost_python3 : boost_python ] converter/from_python.cpp
: # sources converter/registry.cpp
numeric.cpp converter/type_id.cpp
list.cpp object/enum.cpp
long.cpp object/class.cpp
dict.cpp object/function.cpp
tuple.cpp object/inheritance.cpp
str.cpp object/life_support.cpp
slice.cpp object/pickle_support.cpp
errors.cpp
module.cpp
converter/builtin_converters.cpp
converter/arg_to_python_base.cpp
object/iterator.cpp
object/stl_iterator.cpp
object_protocol.cpp
object_operators.cpp
wrapper.cpp
import.cpp
exec.cpp
object/function_doc_signature.cpp
: # requirements
<link>static:<define>BOOST_PYTHON_STATIC_LIB
<define>BOOST_PYTHON_SOURCE
# On Windows, all code using Python has to link to the Python
# import library.
#
# On *nix we never link libboost_python to libpython. When
# extending Python, all Python symbols are provided by the
# Python interpreter executable. When embedding Python, the
# client executable is expected to explicitly link to
# /python//python (the target representing libpython) itself.
#
# python_for_extensions is a target defined by Boost.Build to
# provide the Python include paths, and on Windows, the Python
# import library, as usage requirements.
[ cond [ python.configured ] : <library>/python//python_for_extensions ]
# we prevent building when there is no python available
# as it's not possible anyway, and to cause dependents to
# fail to build
[ unless [ python.configured ] : <build>no ]
converter/from_python.cpp <python-debugging>on:<define>BOOST_DEBUG_PYTHON
converter/registry.cpp : # default build
converter/type_id.cpp <link>shared
object/enum.cpp : # usage requirements
object/class.cpp <link>static:<define>BOOST_PYTHON_STATIC_LIB
object/function.cpp <python-debugging>on:<define>BOOST_DEBUG_PYTHON
object/inheritance.cpp ;
object/life_support.cpp
object/pickle_support.cpp
errors.cpp
module.cpp
converter/builtin_converters.cpp
converter/arg_to_python_base.cpp
object/iterator.cpp
object/stl_iterator.cpp
object_protocol.cpp
object_operators.cpp
wrapper.cpp
import.cpp
exec.cpp
object/function_doc_signature.cpp
: # requirements
<link>static:<define>BOOST_PYTHON_STATIC_LIB
<define>BOOST_PYTHON_SOURCE
# On Windows, all code using Python has to link to the Python
# import library.
#
# On *nix we never link libboost_python to libpython. When
# extending Python, all Python symbols are provided by the
# Python interpreter executable. When embedding Python, the
# client executable is expected to explicitly link to
# /python//python (the target representing libpython) itself.
#
# python_for_extensions is a target defined by Boost.Build to
# provide the Python include paths, and on Windows, the Python
# import library, as usage requirements.
[ cond [ python.configured ] : <library>/python//python_for_extensions ]
# we prevent building when there is no python available
# as it's not possible anyway, and to cause dependents to
# fail to build
[ unless [ python.configured ] : <build>no ]
<dependency>config-warning
<python-debugging>on:<define>BOOST_DEBUG_PYTHON
[ cond $(is-py3) : <python>$(py3-version) ]
: # default build
<link>shared
: # usage requirements
<link>static:<define>BOOST_PYTHON_STATIC_LIB
<python-debugging>on:<define>BOOST_DEBUG_PYTHON
;
}
lib_boost_python ;
boost-install boost_python ; boost-install boost_python ;
if $(py3-version)
{
lib_boost_python yes ;
boost-install boost_python3 ;
}

View File

@@ -1,28 +0,0 @@
// Distributed under the Boost Software License, Version 1.0. (See
// accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)
#include <boost/python/module.hpp>
#include <boost/python/def.hpp>
#include <boost/python/object.hpp>
#include <boost/python/class.hpp>
using namespace boost::python;
struct X
{
int x;
X(int n) : x(n) { }
};
int x_function(X& x)
{ return x.x;
}
BOOST_PYTHON_MODULE(class_ext)
{
class_<X>("X", init<int>());
def("x_function", x_function);
}
#include "module_tail.cpp"

0
doc/PyConDC_2003/bpl.html Executable file → Normal file
View File

0
doc/PyConDC_2003/bpl.pdf Executable file → Normal file
View File

View File

@@ -27,6 +27,7 @@ file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
Somerville, MA 02143 Somerville, MA 02143
:Contact: dave@boost-consulting.com :Contact: dave@boost-consulting.com
:organization: `Boost Consulting`_ :organization: `Boost Consulting`_
:date: $Date$
:status: This is a "work in progress" :status: This is a "work in progress"
:version: 1 :version: 1
:copyright: Copyright David Abrahams 2002. All rights reserved :copyright: Copyright David Abrahams 2002. All rights reserved

View File

@@ -1,6 +1,8 @@
/* /*
:Author: David Goodger :Author: David Goodger
:Contact: goodger@users.sourceforge.net :Contact: goodger@users.sourceforge.net
:date: $Date$
:version: $Revision$
:copyright: This stylesheet has been placed in the public domain. :copyright: This stylesheet has been placed in the public domain.
boostinspect:nolicense boostinspect:nolicense

0
doc/PyConDC_2003/python_cpp_mix.jpg Executable file → Normal file
View File

Before

Width:  |  Height:  |  Size: 22 KiB

After

Width:  |  Height:  |  Size: 22 KiB

0
doc/PyConDC_2003/python_cpp_mix.png Executable file → Normal file
View File

Before

Width:  |  Height:  |  Size: 6.1 KiB

After

Width:  |  Height:  |  Size: 6.1 KiB

View File

@@ -9,7 +9,7 @@
</head> </head>
<body> <body>
<div class="document" id="logo-boost-python-build-and-test-howto"> <div class="document" id="logo-boost-python-build-and-test-howto">
<h1 class="title"><a class="reference external" href="../index.html"><img alt="Boost C++ Libraries:" class="boost-logo" src="../../../boost.png" /></a> Boost.Python Build and Test HOWTO</h1> <h1 class="title"><a class="reference external" href="../index.htm"><img alt="Boost C++ Libraries:" class="boost-logo" src="../../../boost.png" /></a> Boost.Python Build and Test HOWTO</h1>
<!-- Copyright David Abrahams 2006. Distributed under the Boost --> <!-- Copyright David Abrahams 2006. Distributed under the Boost -->
<!-- Software License, Version 1.0. (See accompanying --> <!-- Software License, Version 1.0. (See accompanying -->

0
doc/internals.html Executable file → Normal file
View File

0
doc/internals.rst Executable file → Normal file
View File

View File

@@ -32,43 +32,7 @@
<hr> <hr>
<dl class="page-index"> <dl class="page-index">
<dt>Current SVN</dt> <dt>Current SVN</dt>
<dd>
<ul>
<li>Python 3 support:</li>
<ul>
<li>All the current Boost.Python test cases passed. Extension modules using
Boost.Python expected to support Python 3 smoothly.</li>
<li>Introduced <code>object.contains</code> where <code>x.contains(y)</code>
is equivalent to Python code <code>y in x</code>.
Now <code>dict.has_key</code> is just a wrapper of <code>object.contains</code>.
</li>
<li>When building against Python 3, <code>str.decode</code> will be removed.</li>
<li>When building against Python 3, the original signature of <code>list.sort</code>, which is:
<pre>void sort(object_cref cmpfunc);</pre>
will change to:
<pre>void sort(args_proxy const &args, kwds_proxy const &kwds);</pre>
This is because in Python 3 <code>list.sort</code> requires all its arguments be keyword arguments.
So you should call it like this:
<pre>x.sort(*tuple(), **dict(make_tuple(make_tuple("reverse", true))));</pre>
</li>
<li>According to <a href="http://www.python.org/dev/peps/pep-3123/">PEP 3123</a>,
when building Boost.Python against Python older than 2.6, the following macros will
be defined in Boost.Python header:
<pre>
# define Py_TYPE(o) (((PyObject*)(o))->ob_type)
# define Py_REFCNT(o) (((PyObject*)(o))->ob_refcnt)
# define Py_SIZE(o) (((PyVarObject*)(o))->ob_size)</pre>
So extension writers can use these macro directly, to make code clean and compatible with Python 3.
</li>
</ul>
</ul>
</dd>
<dt>1.39.0 Release</dt>
<dd> <dd>
<ul> <ul>

View File

@@ -396,33 +396,27 @@
</blockquote> </blockquote>
</dd> </dd>
<dt><b><a href="http://pyrap.googlecode.com/">Pyrap</a></b></dt> <dt><b><a href="http://www.rationaldiscovery.com">Rational Discovery
<dd> LLC</a></b></dt>
<p><a href="diepen@astron.nl"
>Ger van Diepen</a> writes:</p>
<blockquote>
<p>Pyrap is the python interface to the Radio-Astronomical Package
casacore (<a href="http://casacore.googlecode.com/"
>casacore.googlecode.com</a>). Astronomers love pyrap because
it makes it easily possible to get their data (observed with
radio-astronomical telescopes like LOFAR, ASKAP, and eVLA) in numpy
arrays and do basic data inspection and manipulation using the many
python packages that are available.</p>
<p>Boost.Python made it quite easily possible to create converters for
the various data types, also for numpy arrays and individual elements
of a numpy array. It's nice they work fully recursively. Mapping C++
functions to Python was straightforward.</p>
</blockquote>
</dd>
<dt><b><a href="http://www.rdkit.org/"
>RDKit: Cheminformatics and Machine Learning Software</a></b></dt>
<dd> <dd>
A collection of cheminformatics and machine-learning software Rational Discovery provides computational modeling, combinatorial
written in C++ and Python. library design and custom software development services to the
pharmaceutical, biotech and chemical industries. We do a substantial
amount of internal research to develop new approaches for applying
machine-learning techniques to solve chemical problems. Because we're a
small organization and chemistry is a large and complex field, it is
essential that we be able to quickly and easily prototype and test new
algorithms.
<p>For our internal software, we implement core data structures in C
and expose them to Python using Boost.Python. Algorithm development is
done in Python and then translated to C if required (often it's not).
This hybrid development approach not only greatly increases our
productivity, but it also allows "non-developers" (people without C
experience) to take part in method development. Learning C is a
daunting task, but "Python fits your brain." (Thanks to Bruce Eckel for
the quote.)</p>
</dd> </dd>
</dl> </dl>

View File

@@ -6,13 +6,11 @@ project boost/libs/python/doc/tutorial/doc ;
import boostbook : boostbook ; import boostbook : boostbook ;
using quickbook ; using quickbook ;
path-constant images : html ;
boostbook tutorial boostbook tutorial
: :
tutorial.qbk tutorial.qbk
: :
<xsl:param>boost.root=../../../../../.. <xsl:param>boost.root=../../../../../..
<format>pdf:<xsl:param>img.src.path=$(images)/ <xsl:param>boost.libraries=../../../../../../libs/libraries.htm
<format>pdf:<xsl:param>boost.url.prefix=http://www.boost.org/doc/libs/release/libs/python/doc/tutorial/doc/html <xsl:param>html.stylesheet=../../../../../../doc/html/boostbook.css
; ;

0
doc/tutorial/doc/html/images/alert.png Executable file → Normal file
View File

Before

Width:  |  Height:  |  Size: 603 B

After

Width:  |  Height:  |  Size: 603 B

0
doc/tutorial/doc/html/images/home.png Executable file → Normal file
View File

Before

Width:  |  Height:  |  Size: 358 B

After

Width:  |  Height:  |  Size: 358 B

0
doc/tutorial/doc/html/images/next.png Executable file → Normal file
View File

Before

Width:  |  Height:  |  Size: 336 B

After

Width:  |  Height:  |  Size: 336 B

0
doc/tutorial/doc/html/images/note.png Executable file → Normal file
View File

Before

Width:  |  Height:  |  Size: 658 B

After

Width:  |  Height:  |  Size: 658 B

0
doc/tutorial/doc/html/images/prev.png Executable file → Normal file
View File

Before

Width:  |  Height:  |  Size: 334 B

After

Width:  |  Height:  |  Size: 334 B

0
doc/tutorial/doc/html/images/tip.png Executable file → Normal file
View File

Before

Width:  |  Height:  |  Size: 640 B

After

Width:  |  Height:  |  Size: 640 B

0
doc/tutorial/doc/html/images/up.png Executable file → Normal file
View File

Before

Width:  |  Height:  |  Size: 370 B

After

Width:  |  Height:  |  Size: 370 B

View File

@@ -1,37 +1,37 @@
<html> <html>
<head> <head>
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII"> <meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
<title>Chapter&#160;1.&#160;python 2.0</title> <title>Chapter 1. python 1.0</title>
<link rel="stylesheet" href="../../../../../../doc/src/boostbook.css" type="text/css"> <link rel="stylesheet" href="../../../../../../doc/html/boostbook.css" type="text/css">
<meta name="generator" content="DocBook XSL Stylesheets V1.76.1"> <meta name="generator" content="DocBook XSL Stylesheets V1.66.1">
<link rel="home" href="index.html" title="Chapter&#160;1.&#160;python 2.0"> <link rel="start" href="index.html" title="Chapter 1. python 1.0">
<link rel="next" href="python/hello.html" title="Building Hello World"> <link rel="next" href="python/hello.html" title=" Building Hello World">
</head> </head>
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"> <body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
<table cellpadding="2" width="100%"><tr> <table cellpadding="2" width="100%"><tr>
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../boost.png"></td> <td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../boost.png"></td>
<td align="center"><a href="../../../../../../index.html">Home</a></td> <td align="center"><a href="../../../../../../index.htm">Home</a></td>
<td align="center"><a href="../../../../../../libs/libraries.htm">Libraries</a></td> <td align="center"><a href="../../../../../../libs/libraries.htm">Libraries</a></td>
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td> <td align="center"><a href="../../../../../../people/people.htm">People</a></td>
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td> <td align="center"><a href="../../../../../../more/faq.htm">FAQ</a></td>
<td align="center"><a href="../../../../../../more/index.htm">More</a></td> <td align="center"><a href="../../../../../../more/index.htm">More</a></td>
</tr></table> </tr></table>
<hr> <hr>
<div class="spirit-nav"><a accesskey="n" href="python/hello.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a></div> <div class="spirit-nav"><a accesskey="n" href="python/hello.html"><img src="../../../../../../doc/html/images/next.png" alt="Next"></a></div>
<div class="chapter"> <div class="chapter" lang="en">
<div class="titlepage"><div> <div class="titlepage"><div>
<div><h2 class="title"> <div><h2 class="title">
<a name="python"></a>Chapter&#160;1.&#160;python 2.0</h2></div> <a name="python"></a>Chapter 1. python 1.0</h2></div>
<div><div class="author"><h3 class="author"> <div><div class="author"><h3 class="author">
<span class="firstname">Joel</span> <span class="surname">de Guzman</span> <span class="firstname">Joel</span> <span class="surname">de Guzman</span>
</h3></div></div> </h3></div></div>
<div><div class="author"><h3 class="author"> <div><div class="author"><h3 class="author">
<span class="firstname">David</span> <span class="surname">Abrahams</span> <span class="firstname">David</span> <span class="surname">Abrahams</span>
</h3></div></div> </h3></div></div>
<div><p class="copyright">Copyright &#169; 2002-2005 Joel <div><p class="copyright">Copyright © 2002-2005 Joel
de Guzman, David Abrahams</p></div> de Guzman, David Abrahams</p></div>
<div><div class="legalnotice"> <div><div class="legalnotice">
<a name="python.legal"></a><p> <a name="id455917"></a><p>
Distributed under the Boost Software License, Version 1.0. (See accompanying Distributed under the Boost Software License, Version 1.0. (See accompanying
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top"> file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">
http://www.boost.org/LICENSE_1_0.txt </a>) http://www.boost.org/LICENSE_1_0.txt </a>)
@@ -42,8 +42,8 @@
<p><b>Table of Contents</b></p> <p><b>Table of Contents</b></p>
<dl> <dl>
<dt><span class="section"><a href="index.html#python.quickstart">QuickStart</a></span></dt> <dt><span class="section"><a href="index.html#python.quickstart">QuickStart</a></span></dt>
<dt><span class="section"><a href="python/hello.html">Building Hello World</a></span></dt> <dt><span class="section"><a href="python/hello.html"> Building Hello World</a></span></dt>
<dt><span class="section"><a href="python/exposing.html">Exposing Classes</a></span></dt> <dt><span class="section"><a href="python/exposing.html"> Exposing Classes</a></span></dt>
<dd><dl> <dd><dl>
<dt><span class="section"><a href="python/exposing.html#python.constructors">Constructors</a></span></dt> <dt><span class="section"><a href="python/exposing.html#python.constructors">Constructors</a></span></dt>
<dt><span class="section"><a href="python/exposing.html#python.class_data_members">Class Data Members</a></span></dt> <dt><span class="section"><a href="python/exposing.html#python.class_data_members">Class Data Members</a></span></dt>
@@ -60,19 +60,18 @@
<dt><span class="section"><a href="python/functions.html#python.default_arguments">Default Arguments</a></span></dt> <dt><span class="section"><a href="python/functions.html#python.default_arguments">Default Arguments</a></span></dt>
<dt><span class="section"><a href="python/functions.html#python.auto_overloading">Auto-Overloading</a></span></dt> <dt><span class="section"><a href="python/functions.html#python.auto_overloading">Auto-Overloading</a></span></dt>
</dl></dd> </dl></dd>
<dt><span class="section"><a href="python/object.html">Object Interface</a></span></dt> <dt><span class="section"><a href="python/object.html"> Object Interface</a></span></dt>
<dd><dl> <dd><dl>
<dt><span class="section"><a href="python/object.html#python.basic_interface">Basic Interface</a></span></dt> <dt><span class="section"><a href="python/object.html#python.basic_interface">Basic Interface</a></span></dt>
<dt><span class="section"><a href="python/object.html#python.derived_object_types">Derived Object types</a></span></dt> <dt><span class="section"><a href="python/object.html#python.derived_object_types">Derived Object types</a></span></dt>
<dt><span class="section"><a href="python/object.html#python.extracting_c___objects">Extracting C++ objects</a></span></dt> <dt><span class="section"><a href="python/object.html#python.extracting_c___objects">Extracting C++ objects</a></span></dt>
<dt><span class="section"><a href="python/object.html#python.enums">Enums</a></span></dt> <dt><span class="section"><a href="python/object.html#python.enums">Enums</a></span></dt>
<dt><span class="section"><a href="python/object.html#python.creating_python_object">Creating <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">python</span><span class="special">::</span><span class="identifier">object</span></code> from <code class="computeroutput"><span class="identifier">PyObject</span><span class="special">*</span></code></a></span></dt>
</dl></dd> </dl></dd>
<dt><span class="section"><a href="python/embedding.html">Embedding</a></span></dt> <dt><span class="section"><a href="python/embedding.html">Embedding</a></span></dt>
<dd><dl><dt><span class="section"><a href="python/embedding.html#python.using_the_interpreter">Using the interpreter</a></span></dt></dl></dd> <dd><dl><dt><span class="section"><a href="python/embedding.html#python.using_the_interpreter">Using the interpreter</a></span></dt></dl></dd>
<dt><span class="section"><a href="python/iterators.html">Iterators</a></span></dt> <dt><span class="section"><a href="python/iterators.html">Iterators</a></span></dt>
<dt><span class="section"><a href="python/exception.html">Exception Translation</a></span></dt> <dt><span class="section"><a href="python/exception.html"> Exception Translation</a></span></dt>
<dt><span class="section"><a href="python/techniques.html">General Techniques</a></span></dt> <dt><span class="section"><a href="python/techniques.html"> General Techniques</a></span></dt>
<dd><dl> <dd><dl>
<dt><span class="section"><a href="python/techniques.html#python.creating_packages">Creating Packages</a></span></dt> <dt><span class="section"><a href="python/techniques.html#python.creating_packages">Creating Packages</a></span></dt>
<dt><span class="section"><a href="python/techniques.html#python.extending_wrapped_objects_in_python">Extending Wrapped Objects in Python</a></span></dt> <dt><span class="section"><a href="python/techniques.html#python.extending_wrapped_objects_in_python">Extending Wrapped Objects in Python</a></span></dt>
@@ -80,7 +79,7 @@
</dl></dd> </dl></dd>
</dl> </dl>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h2 class="title" style="clear: both"> <div class="titlepage"><div><div><h2 class="title" style="clear: both">
<a name="python.quickstart"></a>QuickStart</h2></div></div></div> <a name="python.quickstart"></a>QuickStart</h2></div></div></div>
<p> <p>
@@ -94,15 +93,16 @@
code takes on the look of a kind of declarative interface definition language code takes on the look of a kind of declarative interface definition language
(IDL). (IDL).
</p> </p>
<h3> <a name="quickstart.hello_world"></a><h2>
<a name="quickstart.hello_world"></a> <a name="id385257"></a>
Hello World Hello World
</h3> </h2>
<p> <p>
Following C/C++ tradition, let's start with the "hello, world". A Following C/C++ tradition, let's start with the "hello, world". A
C++ Function: C++ Function:
</p> </p>
<pre class="programlisting"><span class="keyword">char</span> <span class="keyword">const</span><span class="special">*</span> <span class="identifier">greet</span><span class="special">()</span> <pre class="programlisting">
<span class="keyword">char</span> <span class="keyword">const</span><span class="special">*</span> <span class="identifier">greet</span><span class="special">()</span>
<span class="special">{</span> <span class="special">{</span>
<span class="keyword">return</span> <span class="string">"hello, world"</span><span class="special">;</span> <span class="keyword">return</span> <span class="string">"hello, world"</span><span class="special">;</span>
<span class="special">}</span> <span class="special">}</span>
@@ -110,7 +110,8 @@
<p> <p>
can be exposed to Python by writing a Boost.Python wrapper: can be exposed to Python by writing a Boost.Python wrapper:
</p> </p>
<pre class="programlisting"><span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">python</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span> <pre class="programlisting">
<span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">python</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span>
<span class="identifier">BOOST_PYTHON_MODULE</span><span class="special">(</span><span class="identifier">hello_ext</span><span class="special">)</span> <span class="identifier">BOOST_PYTHON_MODULE</span><span class="special">(</span><span class="identifier">hello_ext</span><span class="special">)</span>
<span class="special">{</span> <span class="special">{</span>
@@ -122,21 +123,32 @@
That's it. We're done. We can now build this as a shared library. The resulting That's it. We're done. We can now build this as a shared library. The resulting
DLL is now visible to Python. Here's a sample Python session: DLL is now visible to Python. Here's a sample Python session:
</p> </p>
<pre class="programlisting"><span class="special">&gt;&gt;&gt;</span> <span class="keyword">import</span> <span class="identifier">hello_ext</span> <p>
<span class="special">&gt;&gt;&gt;</span> <span class="keyword">print</span> <span class="identifier">hello_ext</span><span class="special">.</span><span class="identifier">greet</span><span class="special">()</span> </p>
<pre class="programlisting">
<span class="special">&gt;&gt;&gt;</span> <span class="keyword">import</span> <span class="identifier">hello_ext</span>
<span class="special">&gt;&gt;&gt;</span> <span class="keyword">print</span> <span class="identifier">hello</span><span class="special">.</span><span class="identifier">greet</span><span class="special">()</span>
<span class="identifier">hello</span><span class="special">,</span> <span class="identifier">world</span> <span class="identifier">hello</span><span class="special">,</span> <span class="identifier">world</span>
</pre> </pre>
<div class="blockquote"><blockquote class="blockquote"><p> <p>
<span class="emphasis"><em><span class="bold"><strong>Next stop... Building your Hello World module </p>
from start to finish...</strong></span></em></span> <div class="blockquote"><blockquote class="blockquote">
</p></blockquote></div> <p>
</p>
<p>
<span class="emphasis"><em><span class="bold"><b>Next stop... Building your Hello World
module from start to finish...</b></span></em></span>
</p>
<p>
</p>
</blockquote></div>
</div> </div>
</div> </div>
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr> <table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
<td align="left"><p><small>Last revised: December 26, 2011 at 21:58:39 GMT</small></p></td> <td align="left"><p><small>Last revised: November 07, 2007 at 03:34:24 GMT</small></p></td>
<td align="right"><div class="copyright-footer"></div></td> <td align="right"><div class="copyright-footer"></div></td>
</tr></table> </tr></table>
<hr> <hr>
<div class="spirit-nav"><a accesskey="n" href="python/hello.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a></div> <div class="spirit-nav"><a accesskey="n" href="python/hello.html"><img src="../../../../../../doc/html/images/next.png" alt="Next"></a></div>
</body> </body>
</html> </html>

View File

@@ -1,28 +1,28 @@
<html> <html>
<head> <head>
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII"> <meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
<title>Embedding</title> <title>Embedding</title>
<link rel="stylesheet" href="../../../../../../../doc/src/boostbook.css" type="text/css"> <link rel="stylesheet" href="../../../../../../../doc/html/boostbook.css" type="text/css">
<meta name="generator" content="DocBook XSL Stylesheets V1.76.1"> <meta name="generator" content="DocBook XSL Stylesheets V1.66.1">
<link rel="home" href="../index.html" title="Chapter&#160;1.&#160;python 2.0"> <link rel="start" href="../index.html" title="Chapter 1. python 1.0">
<link rel="up" href="../index.html" title="Chapter&#160;1.&#160;python 2.0"> <link rel="up" href="../index.html" title="Chapter 1. python 1.0">
<link rel="prev" href="object.html" title="Object Interface"> <link rel="prev" href="object.html" title=" Object Interface">
<link rel="next" href="iterators.html" title="Iterators"> <link rel="next" href="iterators.html" title="Iterators">
</head> </head>
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"> <body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
<table cellpadding="2" width="100%"><tr> <table cellpadding="2" width="100%"><tr>
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../../boost.png"></td> <td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../../boost.png"></td>
<td align="center"><a href="../../../../../../../index.html">Home</a></td> <td align="center"><a href="../../../../../../../index.htm">Home</a></td>
<td align="center"><a href="../../../../../../../libs/libraries.htm">Libraries</a></td> <td align="center"><a href="../../../../../../../libs/libraries.htm">Libraries</a></td>
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td> <td align="center"><a href="../../../../../../../people/people.htm">People</a></td>
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td> <td align="center"><a href="../../../../../../../more/faq.htm">FAQ</a></td>
<td align="center"><a href="../../../../../../../more/index.htm">More</a></td> <td align="center"><a href="../../../../../../../more/index.htm">More</a></td>
</tr></table> </tr></table>
<hr> <hr>
<div class="spirit-nav"> <div class="spirit-nav">
<a accesskey="p" href="object.html"><img src="../../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="iterators.html"><img src="../../../../../../../doc/src/images/next.png" alt="Next"></a> <a accesskey="p" href="object.html"><img src="../../../../../../../doc/html/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/html/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/html/images/home.png" alt="Home"></a><a accesskey="n" href="iterators.html"><img src="../../../../../../../doc/html/images/next.png" alt="Next"></a>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h2 class="title" style="clear: both"> <div class="titlepage"><div><div><h2 class="title" style="clear: both">
<a name="python.embedding"></a>Embedding</h2></div></div></div> <a name="python.embedding"></a>Embedding</h2></div></div></div>
<div class="toc"><dl><dt><span class="section"><a href="embedding.html#python.using_the_interpreter">Using the interpreter</a></span></dt></dl></div> <div class="toc"><dl><dt><span class="section"><a href="embedding.html#python.using_the_interpreter">Using the interpreter</a></span></dt></dl></div>
@@ -39,28 +39,28 @@
a lot easier and, in a future version, it may become unnecessary to touch the a lot easier and, in a future version, it may become unnecessary to touch the
Python/C API at all. So stay tuned... <span class="inlinemediaobject"><img src="../images/smiley.png" alt="smiley"></span> Python/C API at all. So stay tuned... <span class="inlinemediaobject"><img src="../images/smiley.png" alt="smiley"></span>
</p> </p>
<h3> <a name="embedding.building_embedded_programs"></a><h2>
<a name="embedding.building_embedded_programs"></a> <a name="id471171"></a>
Building embedded programs Building embedded programs
</h3> </h2>
<p> <p>
To be able to embed python into your programs, you have to link to both Boost.Python's To be able to embed python into your programs, you have to link to both Boost.Python's
as well as Python's own runtime library. as well as Python's own runtime library.
</p> </p>
<p> <p>
Boost.Python's library comes in two variants. Both are located in Boost's Boost.Python's library comes in two variants. Both are located in Boost's
<code class="literal">/libs/python/build/bin-stage</code> subdirectory. On Windows, the <tt class="literal">/libs/python/build/bin-stage</tt> subdirectory. On Windows, the
variants are called <code class="literal">boost_python.lib</code> (for release builds) variants are called <tt class="literal">boost_python.lib</tt> (for release builds)
and <code class="literal">boost_python_debug.lib</code> (for debugging). If you can't and <tt class="literal">boost_python_debug.lib</tt> (for debugging). If you can't
find the libraries, you probably haven't built Boost.Python yet. See <a href="../../../../building.html" target="_top">Building and Testing</a> on how to do this. find the libraries, you probably haven't built Boost.Python yet. See <a href="../../../../building.html" target="_top">Building and Testing</a> on how to do this.
</p> </p>
<p> <p>
Python's library can be found in the <code class="literal">/libs</code> subdirectory Python's library can be found in the <tt class="literal">/libs</tt> subdirectory
of your Python directory. On Windows it is called pythonXY.lib where X.Y is of your Python directory. On Windows it is called pythonXY.lib where X.Y is
your major Python version number. your major Python version number.
</p> </p>
<p> <p>
Additionally, Python's <code class="literal">/include</code> subdirectory has to be added Additionally, Python's <tt class="literal">/include</tt> subdirectory has to be added
to your include path. to your include path.
</p> </p>
<p> <p>
@@ -81,64 +81,72 @@ exe embedded_program # name of the executable
&lt;library-path&gt;$(PYTHON_LIB_PATH) &lt;library-path&gt;$(PYTHON_LIB_PATH)
&lt;find-library&gt;$(PYTHON_EMBEDDED_LIBRARY) ; &lt;find-library&gt;$(PYTHON_EMBEDDED_LIBRARY) ;
</pre> </pre>
<h3> <a name="embedding.getting_started"></a><h2>
<a name="embedding.getting_started"></a> <a name="id471276"></a>
Getting started Getting started
</h3> </h2>
<p> <p>
Being able to build is nice, but there is nothing to build yet. Embedding the Being able to build is nice, but there is nothing to build yet. Embedding the
Python interpreter into one of your C++ programs requires these 4 steps: Python interpreter into one of your C++ programs requires these 4 steps:
</p> </p>
<div class="orderedlist"><ol class="orderedlist" type="1"> <div class="orderedlist"><ol type="1">
<li class="listitem"> <li>
#include <code class="literal">&lt;boost/python.hpp&gt;</code> #include <tt class="literal">&lt;boost/python.hpp&gt;</tt>
</li> </li>
<li class="listitem"> <li>
Call <a href="http://www.python.org/doc/current/api/initialization.html#l2h-652" target="_top">Py_Initialize</a>() Call <a href="http://www.python.org/doc/current/api/initialization.html#l2h-652" target="_top">Py_Initialize</a>()
to start the interpreter and create the <code class="literal">__main__</code> module. to start the interpreter and create the <tt class="literal"><span class="underline">_main</span>_</tt>
</li> module.
<li class="listitem"> </li>
Call other Python C API routines to use the interpreter. <li>
</li> Call other Python C API routines to use the interpreter.
</li>
</ol></div> </ol></div>
<div class="note"><table border="0" summary="Note"> <div class="note"><table border="0" summary="Note">
<tr> <tr>
<td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../../../doc/src/images/note.png"></td> <td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../../../doc/html/images/note.png"></td>
<th align="left">Note</th> <th align="left">Note</th>
</tr> </tr>
<tr><td align="left" valign="top"><p> <tr><td colspan="2" align="left" valign="top"><p>
<span class="bold"><strong>Note that at this time you must not call <a href="http://www.python.org/doc/current/api/initialization.html#l2h-656" target="_top">Py_Finalize</a>() <span class="bold"><b>Note that at this time you must not call <a href="http://www.python.org/doc/current/api/initialization.html#l2h-656" target="_top">Py_Finalize</a>()
to stop the interpreter. This may be fixed in a future version of boost.python.</strong></span> to stop the interpreter. This may be fixed in a future version of boost.python.</b></span>
</p></td></tr> </p></td></tr>
</table></div> </table></div>
<p> <p>
(Of course, there can be other C++ code between all of these steps.) (Of course, there can be other C++ code between all of these steps.)
</p> </p>
<div class="blockquote"><blockquote class="blockquote"><p> <div class="blockquote"><blockquote class="blockquote">
<span class="emphasis"><em><span class="bold"><strong>Now that we can embed the interpreter in <p>
our programs, lets see how to put it to use...</strong></span></em></span> </p>
</p></blockquote></div> <p>
<div class="section"> <span class="emphasis"><em><span class="bold"><b>Now that we can embed the interpreter in
our programs, lets see how to put it to use...</b></span></em></span>
</p>
<p>
</p>
</blockquote></div>
<div class="section" lang="en">
<div class="titlepage"><div><div><h3 class="title"> <div class="titlepage"><div><div><h3 class="title">
<a name="python.using_the_interpreter"></a>Using the interpreter</h3></div></div></div> <a name="python.using_the_interpreter"></a>Using the interpreter</h3></div></div></div>
<p> <p>
As you probably already know, objects in Python are reference-counted. Naturally, As you probably already know, objects in Python are reference-counted. Naturally,
the <code class="literal">PyObject</code>s of the Python C API are also reference-counted. the <tt class="literal">PyObject</tt>s of the Python/C API are also reference-counted.
There is a difference however. While the reference-counting is fully automatic There is a difference however. While the reference-counting is fully automatic
in Python, the Python C API requires you to do it <a href="http://www.python.org/doc/current/c-api/refcounting.html" target="_top">by in Python, the Python<span class="emphasis"><em>C API requires you to do it [@http:</em></span>/www.python.org/doc/current/api/refcounts.html
hand</a>. This is messy and especially hard to get right in the presence by hand]. This is messy and especially hard to get right in the presence
of C++ exceptions. Fortunately Boost.Python provides the <a href="../../../../v2/handle.html" target="_top">handle</a> of C++ exceptions. Fortunately Boost.Python provides the <a href="../../../../v2/handle.html" target="_top">handle</a>
and <a href="../../../../v2/object.html" target="_top">object</a> class templates to and <a href="../../../../v2/object.html" target="_top">object</a> class templates to
automate the process. automate the process.
</p> </p>
<h3> <a name="using_the_interpreter.running_python_code"></a><h2>
<a name="using_the_interpreter.running_python_code"></a> <a name="id471439"></a>
Running Python code Running Python code
</h3> </h2>
<p> <p>
Boost.python provides three related functions to run Python code from C++. Boost.python provides three related functions to run Python code from C++.
</p> </p>
<pre class="programlisting"><span class="identifier">object</span> <span class="identifier">eval</span><span class="special">(</span><span class="identifier">str</span> <span class="identifier">expression</span><span class="special">,</span> <span class="identifier">object</span> <span class="identifier">globals</span> <span class="special">=</span> <span class="identifier">object</span><span class="special">(),</span> <span class="identifier">object</span> <span class="identifier">locals</span> <span class="special">=</span> <span class="identifier">object</span><span class="special">())</span> <pre class="programlisting">
<span class="identifier">object</span> <span class="identifier">eval</span><span class="special">(</span><span class="identifier">str</span> <span class="identifier">expression</span><span class="special">,</span> <span class="identifier">object</span> <span class="identifier">globals</span> <span class="special">=</span> <span class="identifier">object</span><span class="special">(),</span> <span class="identifier">object</span> <span class="identifier">locals</span> <span class="special">=</span> <span class="identifier">object</span><span class="special">())</span>
<span class="identifier">object</span> <span class="identifier">exec</span><span class="special">(</span><span class="identifier">str</span> <span class="identifier">code</span><span class="special">,</span> <span class="identifier">object</span> <span class="identifier">globals</span> <span class="special">=</span> <span class="identifier">object</span><span class="special">(),</span> <span class="identifier">object</span> <span class="identifier">locals</span> <span class="special">=</span> <span class="identifier">object</span><span class="special">())</span> <span class="identifier">object</span> <span class="identifier">exec</span><span class="special">(</span><span class="identifier">str</span> <span class="identifier">code</span><span class="special">,</span> <span class="identifier">object</span> <span class="identifier">globals</span> <span class="special">=</span> <span class="identifier">object</span><span class="special">(),</span> <span class="identifier">object</span> <span class="identifier">locals</span> <span class="special">=</span> <span class="identifier">object</span><span class="special">())</span>
<span class="identifier">object</span> <span class="identifier">exec_file</span><span class="special">(</span><span class="identifier">str</span> <span class="identifier">filename</span><span class="special">,</span> <span class="identifier">object</span> <span class="identifier">globals</span> <span class="special">=</span> <span class="identifier">object</span><span class="special">(),</span> <span class="identifier">object</span> <span class="identifier">locals</span> <span class="special">=</span> <span class="identifier">object</span><span class="special">())</span> <span class="identifier">object</span> <span class="identifier">exec_file</span><span class="special">(</span><span class="identifier">str</span> <span class="identifier">filename</span><span class="special">,</span> <span class="identifier">object</span> <span class="identifier">globals</span> <span class="special">=</span> <span class="identifier">object</span><span class="special">(),</span> <span class="identifier">object</span> <span class="identifier">locals</span> <span class="special">=</span> <span class="identifier">object</span><span class="special">())</span>
</pre> </pre>
@@ -148,25 +156,28 @@ exe embedded_program # name of the executable
and exec_file executes the code contained in the given file. and exec_file executes the code contained in the given file.
</p> </p>
<p> <p>
The <code class="literal">globals</code> and <code class="literal">locals</code> parameters are The <tt class="literal">globals</tt> and <tt class="literal">locals</tt> parameters are
Python dictionaries containing the globals and locals of the context in which Python dictionaries containing the globals and locals of the context in which
to run the code. For most intents and purposes you can use the namespace to run the code. For most intents and purposes you can use the namespace
dictionary of the <code class="literal">__main__</code> module for both parameters. dictionary of the <tt class="literal"><span class="underline">_main</span>_</tt>
module for both parameters.
</p> </p>
<p> <p>
Boost.python provides a function to import a module: Boost.python provides a function to import a module:
</p> </p>
<pre class="programlisting"><span class="identifier">object</span> <span class="identifier">import</span><span class="special">(</span><span class="identifier">str</span> <span class="identifier">name</span><span class="special">)</span> <pre class="programlisting">
<span class="identifier">object</span> <span class="identifier">import</span><span class="special">(</span><span class="identifier">str</span> <span class="identifier">name</span><span class="special">)</span>
</pre> </pre>
<p> <p>
import imports a python module (potentially loading it into the running process import imports a python module (potentially loading it into the running process
first), and returns it. first), and returns it.
</p> </p>
<p> <p>
Let's import the <code class="literal">__main__</code> module and run some Python code Let's import the <tt class="literal"><span class="underline">_main</span>_</tt>
in its namespace: module and run some Python code in its namespace:
</p> </p>
<pre class="programlisting"><span class="identifier">object</span> <span class="identifier">main_module</span> <span class="special">=</span> <span class="identifier">import</span><span class="special">(</span><span class="string">"__main__"</span><span class="special">);</span> <pre class="programlisting">
<span class="identifier">object</span> <span class="identifier">main_module</span> <span class="special">=</span> <span class="identifier">import</span><span class="special">(</span><span class="string">"__main__"</span><span class="special">);</span>
<span class="identifier">object</span> <span class="identifier">main_namespace</span> <span class="special">=</span> <span class="identifier">main_module</span><span class="special">.</span><span class="identifier">attr</span><span class="special">(</span><span class="string">"__dict__"</span><span class="special">);</span> <span class="identifier">object</span> <span class="identifier">main_namespace</span> <span class="special">=</span> <span class="identifier">main_module</span><span class="special">.</span><span class="identifier">attr</span><span class="special">(</span><span class="string">"__dict__"</span><span class="special">);</span>
<span class="identifier">object</span> <span class="identifier">ignored</span> <span class="special">=</span> <span class="identifier">exec</span><span class="special">(</span><span class="string">"hello = file('hello.txt', 'w')\n"</span> <span class="identifier">object</span> <span class="identifier">ignored</span> <span class="special">=</span> <span class="identifier">exec</span><span class="special">(</span><span class="string">"hello = file('hello.txt', 'w')\n"</span>
@@ -178,70 +189,74 @@ exe embedded_program # name of the executable
This should create a file called 'hello.txt' in the current directory containing This should create a file called 'hello.txt' in the current directory containing
a phrase that is well-known in programming circles. a phrase that is well-known in programming circles.
</p> </p>
<h3> <a name="using_the_interpreter.manipulating_python_objects"></a><h2>
<a name="using_the_interpreter.manipulating_python_objects"></a> <a name="id472027"></a>
Manipulating Python objects Manipulating Python objects
</h3> </h2>
<p> <p>
Often we'd like to have a class to manipulate Python objects. But we have Often we'd like to have a class to manipulate Python objects. But we have
already seen such a class above, and in the <a href="object.html" target="_top">previous already seen such a class above, and in the <a href="object.html" target="_top">previous
section</a>: the aptly named <code class="literal">object</code> class and its section</a>: the aptly named <tt class="literal">object</tt> class and its
derivatives. We've already seen that they can be constructed from a <code class="literal">handle</code>. derivatives. We've already seen that they can be constructed from a <tt class="literal">handle</tt>.
The following examples should further illustrate this fact: The following examples should further illustrate this fact:
</p> </p>
<pre class="programlisting"><span class="identifier">object</span> <span class="identifier">main_module</span> <span class="special">=</span> <span class="identifier">import</span><span class="special">(</span><span class="string">"__main__"</span><span class="special">);</span> <pre class="programlisting">
<span class="identifier">object</span> <span class="identifier">main_module</span> <span class="special">=</span> <span class="identifier">import</span><span class="special">(</span><span class="string">"__main__"</span><span class="special">);</span>
<span class="identifier">object</span> <span class="identifier">main_namespace</span> <span class="special">=</span> <span class="identifier">main_module</span><span class="special">.</span><span class="identifier">attr</span><span class="special">(</span><span class="string">"__dict__"</span><span class="special">);</span> <span class="identifier">object</span> <span class="identifier">main_namespace</span> <span class="special">=</span> <span class="identifier">main_module</span><span class="special">.</span><span class="identifier">attr</span><span class="special">(</span><span class="string">"__dict__"</span><span class="special">);</span>
<span class="identifier">object</span> <span class="identifier">ignored</span> <span class="special">=</span> <span class="identifier">exec</span><span class="special">(</span><span class="string">"result = 5 ** 2"</span><span class="special">,</span> <span class="identifier">main_namespace</span><span class="special">);</span> <span class="identifier">object</span> <span class="identifier">ignored</span> <span class="special">=</span> <span class="identifier">exec</span><span class="special">(</span><span class="string">"result = 5 ** 2"</span><span class="special">,</span> <span class="identifier">main_namespace</span><span class="special">);</span>
<span class="keyword">int</span> <span class="identifier">five_squared</span> <span class="special">=</span> <span class="identifier">extract</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;(</span><span class="identifier">main_namespace</span><span class="special">[</span><span class="string">"result"</span><span class="special">]);</span> <span class="keyword">int</span> <span class="identifier">five_squared</span> <span class="special">=</span> <span class="identifier">extract</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;(</span><span class="identifier">main_namespace</span><span class="special">[</span><span class="string">"result"</span><span class="special">]);</span>
</pre> </pre>
<p> <p>
Here we create a dictionary object for the <code class="literal">__main__</code> module's Here we create a dictionary object for the <tt class="literal"><span class="underline">_main</span>_</tt>
namespace. Then we assign 5 squared to the result variable and read this module's namespace. Then we assign 5 squared to the result variable and read
variable from the dictionary. Another way to achieve the same result is to this variable from the dictionary. Another way to achieve the same result
use eval instead, which returns the result directly: is to use eval instead, which returns the result directly:
</p> </p>
<pre class="programlisting"><span class="identifier">object</span> <span class="identifier">result</span> <span class="special">=</span> <span class="identifier">eval</span><span class="special">(</span><span class="string">"5 ** 2"</span><span class="special">);</span> <pre class="programlisting">
<span class="identifier">object</span> <span class="identifier">result</span> <span class="special">=</span> <span class="identifier">eval</span><span class="special">(</span><span class="string">"5 ** 2"</span><span class="special">);</span>
<span class="keyword">int</span> <span class="identifier">five_squared</span> <span class="special">=</span> <span class="identifier">extract</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;(</span><span class="identifier">result</span><span class="special">);</span> <span class="keyword">int</span> <span class="identifier">five_squared</span> <span class="special">=</span> <span class="identifier">extract</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;(</span><span class="identifier">result</span><span class="special">);</span>
</pre> </pre>
<h3> <a name="using_the_interpreter.exception_handling"></a><h2>
<a name="using_the_interpreter.exception_handling"></a> <a name="id472399"></a>
Exception handling Exception handling
</h3> </h2>
<p> <p>
If an exception occurs in the evaluation of the python expression, <a href="../../../../v2/errors.html#error_already_set-spec" target="_top">error_already_set</a> If an exception occurs in the evaluation of the python expression, <a href="../../../../v2/errors.html#error_already_set-spec" target="_top">error_already_set</a>
is thrown: is thrown:
</p> </p>
<pre class="programlisting"><span class="keyword">try</span> <pre class="programlisting">
<span class="keyword">try</span>
<span class="special">{</span> <span class="special">{</span>
<span class="identifier">object</span> <span class="identifier">result</span> <span class="special">=</span> <span class="identifier">eval</span><span class="special">(</span><span class="string">"5/0"</span><span class="special">);</span> <span class="identifier">object</span> <span class="identifier">result</span> <span class="special">=</span> <span class="identifier">eval</span><span class="special">(</span><span class="string">"5/0"</span><span class="special">);</span>
<span class="comment">// execution will never get here:</span> <span class="comment">// execution will never get here:
<span class="keyword">int</span> <span class="identifier">five_divided_by_zero</span> <span class="special">=</span> <span class="identifier">extract</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;(</span><span class="identifier">result</span><span class="special">);</span> </span> <span class="keyword">int</span> <span class="identifier">five_divided_by_zero</span> <span class="special">=</span> <span class="identifier">extract</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;(</span><span class="identifier">result</span><span class="special">);</span>
<span class="special">}</span> <span class="special">}</span>
<span class="keyword">catch</span><span class="special">(</span><span class="identifier">error_already_set</span> <span class="keyword">const</span> <span class="special">&amp;)</span> <span class="keyword">catch</span><span class="special">(</span><span class="identifier">error_already_set</span> <span class="keyword">const</span> <span class="special">&amp;)</span>
<span class="special">{</span> <span class="special">{</span>
<span class="comment">// handle the exception in some way</span> <span class="comment">// handle the exception in some way
<span class="special">}</span> </span><span class="special">}</span>
</pre> </pre>
<p> <p>
The <code class="literal">error_already_set</code> exception class doesn't carry any The <tt class="literal">error_already_set</tt> exception class doesn't carry any
information in itself. To find out more about the Python exception that occurred, information in itself. To find out more about the Python exception that occurred,
you need to use the <a href="http://www.python.org/doc/api/exceptionHandling.html" target="_top">exception you need to use the <a href="http://www.python.org/doc/api/exceptionHandling.html" target="_top">exception
handling functions</a> of the Python C API in your catch-statement. This handling functions</a> of the Python<span class="emphasis"><em>C API in your catch-statement.
can be as simple as calling <a href="http://www.python.org/doc/api/exceptionHandling.html#l2h-70" target="_top">PyErr_Print()</a> This can be as simple as calling [@http:</em></span>/www.python.org/doc/api/exceptionHandling.html#l2h-70
to print the exception's traceback to the console, or comparing the type PyErr_Print()] to print the exception's traceback to the console, or comparing
of the exception with those of the <a href="http://www.python.org/doc/api/standardExceptions.html" target="_top">standard the type of the exception with those of the <a href="http://www.python.org/doc/api/standardExceptions.html" target="_top">standard
exceptions</a>: exceptions</a>:
</p> </p>
<pre class="programlisting"><span class="keyword">catch</span><span class="special">(</span><span class="identifier">error_already_set</span> <span class="keyword">const</span> <span class="special">&amp;)</span> <pre class="programlisting">
<span class="keyword">catch</span><span class="special">(</span><span class="identifier">error_already_set</span> <span class="keyword">const</span> <span class="special">&amp;)</span>
<span class="special">{</span> <span class="special">{</span>
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">PyErr_ExceptionMatches</span><span class="special">(</span><span class="identifier">PyExc_ZeroDivisionError</span><span class="special">))</span> <span class="keyword">if</span> <span class="special">(</span><span class="identifier">PyErr_ExceptionMatches</span><span class="special">(</span><span class="identifier">PyExc_ZeroDivisionError</span><span class="special">))</span>
<span class="special">{</span> <span class="special">{</span>
<span class="comment">// handle ZeroDivisionError specially</span> <span class="comment">// handle ZeroDivisionError specially
<span class="special">}</span> </span> <span class="special">}</span>
<span class="keyword">else</span> <span class="keyword">else</span>
<span class="special">{</span> <span class="special">{</span>
<span class="comment">// print all other errors to stderr</span> <span class="comment">// print all other errors to stderr
<span class="identifier">PyErr_Print</span><span class="special">();</span> </span> <span class="identifier">PyErr_Print</span><span class="special">();</span>
<span class="special">}</span> <span class="special">}</span>
<span class="special">}</span> <span class="special">}</span>
</pre> </pre>
@@ -253,7 +268,7 @@ exe embedded_program # name of the executable
</div> </div>
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr> <table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
<td align="left"></td> <td align="left"></td>
<td align="right"><div class="copyright-footer">Copyright &#169; 2002-2005 Joel <td align="right"><div class="copyright-footer">Copyright © 2002-2005 Joel
de Guzman, David Abrahams<p> de Guzman, David Abrahams<p>
Distributed under the Boost Software License, Version 1.0. (See accompanying Distributed under the Boost Software License, Version 1.0. (See accompanying
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top"> file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">
@@ -263,7 +278,7 @@ exe embedded_program # name of the executable
</tr></table> </tr></table>
<hr> <hr>
<div class="spirit-nav"> <div class="spirit-nav">
<a accesskey="p" href="object.html"><img src="../../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="iterators.html"><img src="../../../../../../../doc/src/images/next.png" alt="Next"></a> <a accesskey="p" href="object.html"><img src="../../../../../../../doc/html/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/html/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/html/images/home.png" alt="Home"></a><a accesskey="n" href="iterators.html"><img src="../../../../../../../doc/html/images/next.png" alt="Next"></a>
</div> </div>
</body> </body>
</html> </html>

View File

@@ -1,41 +1,43 @@
<html> <html>
<head> <head>
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII"> <meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
<title>Exception Translation</title> <title> Exception Translation</title>
<link rel="stylesheet" href="../../../../../../../doc/src/boostbook.css" type="text/css"> <link rel="stylesheet" href="../../../../../../../doc/html/boostbook.css" type="text/css">
<meta name="generator" content="DocBook XSL Stylesheets V1.76.1"> <meta name="generator" content="DocBook XSL Stylesheets V1.66.1">
<link rel="home" href="../index.html" title="Chapter&#160;1.&#160;python 2.0"> <link rel="start" href="../index.html" title="Chapter 1. python 1.0">
<link rel="up" href="../index.html" title="Chapter&#160;1.&#160;python 2.0"> <link rel="up" href="../index.html" title="Chapter 1. python 1.0">
<link rel="prev" href="iterators.html" title="Iterators"> <link rel="prev" href="iterators.html" title="Iterators">
<link rel="next" href="techniques.html" title="General Techniques"> <link rel="next" href="techniques.html" title=" General Techniques">
</head> </head>
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"> <body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
<table cellpadding="2" width="100%"><tr> <table cellpadding="2" width="100%"><tr>
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../../boost.png"></td> <td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../../boost.png"></td>
<td align="center"><a href="../../../../../../../index.html">Home</a></td> <td align="center"><a href="../../../../../../../index.htm">Home</a></td>
<td align="center"><a href="../../../../../../../libs/libraries.htm">Libraries</a></td> <td align="center"><a href="../../../../../../../libs/libraries.htm">Libraries</a></td>
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td> <td align="center"><a href="../../../../../../../people/people.htm">People</a></td>
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td> <td align="center"><a href="../../../../../../../more/faq.htm">FAQ</a></td>
<td align="center"><a href="../../../../../../../more/index.htm">More</a></td> <td align="center"><a href="../../../../../../../more/index.htm">More</a></td>
</tr></table> </tr></table>
<hr> <hr>
<div class="spirit-nav"> <div class="spirit-nav">
<a accesskey="p" href="iterators.html"><img src="../../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="techniques.html"><img src="../../../../../../../doc/src/images/next.png" alt="Next"></a> <a accesskey="p" href="iterators.html"><img src="../../../../../../../doc/html/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/html/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/html/images/home.png" alt="Home"></a><a accesskey="n" href="techniques.html"><img src="../../../../../../../doc/html/images/next.png" alt="Next"></a>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h2 class="title" style="clear: both"> <div class="titlepage"><div><div><h2 class="title" style="clear: both">
<a name="python.exception"></a>Exception Translation</h2></div></div></div> <a name="python.exception"></a> Exception Translation</h2></div></div></div>
<p> <p>
All C++ exceptions must be caught at the boundary with Python code. This boundary All C++ exceptions must be caught at the boundary with Python code. This boundary
is the point where C++ meets Python. Boost.Python provides a default exception is the point where C++ meets Python. Boost.Python provides a default exception
handler that translates selected standard exceptions, then gives up: handler that translates selected standard exceptions, then gives up:
</p> </p>
<pre class="programlisting"><span class="keyword">raise</span> <span class="identifier">RuntimeError</span><span class="special">,</span> <span class="string">'unidentifiable C++ Exception'</span> <pre class="programlisting">
<span class="keyword">raise</span> <span class="identifier">RuntimeError</span><span class="special">,</span> <span class="string">'unidentifiable C++ Exception'</span>
</pre> </pre>
<p> <p>
Users may provide custom translation. Here's an example: Users may provide custom translation. Here's an example:
</p> </p>
<pre class="programlisting"><span class="identifier">struct</span> <span class="identifier">PodBayDoorException</span><span class="special">;</span> <pre class="programlisting">
<span class="identifier">struct</span> <span class="identifier">PodBayDoorException</span><span class="special">;</span>
<span class="identifier">void</span> <span class="identifier">translator</span><span class="special">(</span><span class="identifier">PodBayDoorException</span> <span class="identifier">const</span><span class="special">&amp;</span> <span class="identifier">x</span><span class="special">)</span> <span class="special">{</span> <span class="identifier">void</span> <span class="identifier">translator</span><span class="special">(</span><span class="identifier">PodBayDoorException</span> <span class="identifier">const</span><span class="special">&amp;</span> <span class="identifier">x</span><span class="special">)</span> <span class="special">{</span>
<span class="identifier">PyErr_SetString</span><span class="special">(</span><span class="identifier">PyExc_UserWarning</span><span class="special">,</span> <span class="string">"I'm sorry Dave..."</span><span class="special">);</span> <span class="identifier">PyErr_SetString</span><span class="special">(</span><span class="identifier">PyExc_UserWarning</span><span class="special">,</span> <span class="string">"I'm sorry Dave..."</span><span class="special">);</span>
<span class="special">}</span> <span class="special">}</span>
@@ -47,7 +49,7 @@
</div> </div>
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr> <table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
<td align="left"></td> <td align="left"></td>
<td align="right"><div class="copyright-footer">Copyright &#169; 2002-2005 Joel <td align="right"><div class="copyright-footer">Copyright © 2002-2005 Joel
de Guzman, David Abrahams<p> de Guzman, David Abrahams<p>
Distributed under the Boost Software License, Version 1.0. (See accompanying Distributed under the Boost Software License, Version 1.0. (See accompanying
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top"> file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">
@@ -57,7 +59,7 @@
</tr></table> </tr></table>
<hr> <hr>
<div class="spirit-nav"> <div class="spirit-nav">
<a accesskey="p" href="iterators.html"><img src="../../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="techniques.html"><img src="../../../../../../../doc/src/images/next.png" alt="Next"></a> <a accesskey="p" href="iterators.html"><img src="../../../../../../../doc/html/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/html/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/html/images/home.png" alt="Home"></a><a accesskey="n" href="techniques.html"><img src="../../../../../../../doc/html/images/next.png" alt="Next"></a>
</div> </div>
</body> </body>
</html> </html>

View File

@@ -1,30 +1,30 @@
<html> <html>
<head> <head>
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII"> <meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
<title>Exposing Classes</title> <title> Exposing Classes</title>
<link rel="stylesheet" href="../../../../../../../doc/src/boostbook.css" type="text/css"> <link rel="stylesheet" href="../../../../../../../doc/html/boostbook.css" type="text/css">
<meta name="generator" content="DocBook XSL Stylesheets V1.76.1"> <meta name="generator" content="DocBook XSL Stylesheets V1.66.1">
<link rel="home" href="../index.html" title="Chapter&#160;1.&#160;python 2.0"> <link rel="start" href="../index.html" title="Chapter 1. python 1.0">
<link rel="up" href="../index.html" title="Chapter&#160;1.&#160;python 2.0"> <link rel="up" href="../index.html" title="Chapter 1. python 1.0">
<link rel="prev" href="hello.html" title="Building Hello World"> <link rel="prev" href="hello.html" title=" Building Hello World">
<link rel="next" href="functions.html" title="Functions"> <link rel="next" href="functions.html" title="Functions">
</head> </head>
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"> <body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
<table cellpadding="2" width="100%"><tr> <table cellpadding="2" width="100%"><tr>
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../../boost.png"></td> <td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../../boost.png"></td>
<td align="center"><a href="../../../../../../../index.html">Home</a></td> <td align="center"><a href="../../../../../../../index.htm">Home</a></td>
<td align="center"><a href="../../../../../../../libs/libraries.htm">Libraries</a></td> <td align="center"><a href="../../../../../../../libs/libraries.htm">Libraries</a></td>
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td> <td align="center"><a href="../../../../../../../people/people.htm">People</a></td>
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td> <td align="center"><a href="../../../../../../../more/faq.htm">FAQ</a></td>
<td align="center"><a href="../../../../../../../more/index.htm">More</a></td> <td align="center"><a href="../../../../../../../more/index.htm">More</a></td>
</tr></table> </tr></table>
<hr> <hr>
<div class="spirit-nav"> <div class="spirit-nav">
<a accesskey="p" href="hello.html"><img src="../../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="functions.html"><img src="../../../../../../../doc/src/images/next.png" alt="Next"></a> <a accesskey="p" href="hello.html"><img src="../../../../../../../doc/html/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/html/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/html/images/home.png" alt="Home"></a><a accesskey="n" href="functions.html"><img src="../../../../../../../doc/html/images/next.png" alt="Next"></a>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h2 class="title" style="clear: both"> <div class="titlepage"><div><div><h2 class="title" style="clear: both">
<a name="python.exposing"></a>Exposing Classes</h2></div></div></div> <a name="python.exposing"></a> Exposing Classes</h2></div></div></div>
<div class="toc"><dl> <div class="toc"><dl>
<dt><span class="section"><a href="exposing.html#python.constructors">Constructors</a></span></dt> <dt><span class="section"><a href="exposing.html#python.constructors">Constructors</a></span></dt>
<dt><span class="section"><a href="exposing.html#python.class_data_members">Class Data Members</a></span></dt> <dt><span class="section"><a href="exposing.html#python.class_data_members">Class Data Members</a></span></dt>
@@ -40,7 +40,8 @@
<p> <p>
Consider a C++ class/struct that we want to expose to Python: Consider a C++ class/struct that we want to expose to Python:
</p> </p>
<pre class="programlisting"><span class="keyword">struct</span> <span class="identifier">World</span> <pre class="programlisting">
<span class="keyword">struct</span> <span class="identifier">World</span>
<span class="special">{</span> <span class="special">{</span>
<span class="keyword">void</span> <span class="identifier">set</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">msg</span><span class="special">)</span> <span class="special">{</span> <span class="keyword">this</span><span class="special">-&gt;</span><span class="identifier">msg</span> <span class="special">=</span> <span class="identifier">msg</span><span class="special">;</span> <span class="special">}</span> <span class="keyword">void</span> <span class="identifier">set</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">msg</span><span class="special">)</span> <span class="special">{</span> <span class="keyword">this</span><span class="special">-&gt;</span><span class="identifier">msg</span> <span class="special">=</span> <span class="identifier">msg</span><span class="special">;</span> <span class="special">}</span>
<span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">greet</span><span class="special">()</span> <span class="special">{</span> <span class="keyword">return</span> <span class="identifier">msg</span><span class="special">;</span> <span class="special">}</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">greet</span><span class="special">()</span> <span class="special">{</span> <span class="keyword">return</span> <span class="identifier">msg</span><span class="special">;</span> <span class="special">}</span>
@@ -50,7 +51,8 @@
<p> <p>
We can expose this to Python by writing a corresponding Boost.Python C++ Wrapper: We can expose this to Python by writing a corresponding Boost.Python C++ Wrapper:
</p> </p>
<pre class="programlisting"><span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">python</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span> <pre class="programlisting">
<span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">python</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span>
<span class="keyword">using</span> <span class="keyword">namespace</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">python</span><span class="special">;</span> <span class="keyword">using</span> <span class="keyword">namespace</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">python</span><span class="special">;</span>
<span class="identifier">BOOST_PYTHON_MODULE</span><span class="special">(</span><span class="identifier">hello</span><span class="special">)</span> <span class="identifier">BOOST_PYTHON_MODULE</span><span class="special">(</span><span class="identifier">hello</span><span class="special">)</span>
@@ -62,47 +64,55 @@
<span class="special">}</span> <span class="special">}</span>
</pre> </pre>
<p> <p>
Here, we wrote a C++ class wrapper that exposes the member functions <code class="literal">greet</code> Here, we wrote a C++ class wrapper that exposes the member functions <tt class="literal">greet</tt>
and <code class="literal">set</code>. Now, after building our module as a shared library, and <tt class="literal">set</tt>. Now, after building our module as a shared library,
we may use our class <code class="literal">World</code> in Python. Here's a sample Python we may use our class <tt class="literal">World</tt> in Python. Here's a sample Python
session: session:
</p> </p>
<pre class="programlisting"><span class="special">&gt;&gt;&gt;</span> <span class="keyword">import</span> <span class="identifier">hello</span> <p>
</p>
<pre class="programlisting">
<span class="special">&gt;&gt;&gt;</span> <span class="keyword">import</span> <span class="identifier">hello</span>
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">planet</span> <span class="special">=</span> <span class="identifier">hello</span><span class="special">.</span><span class="identifier">World</span><span class="special">()</span> <span class="special">&gt;&gt;&gt;</span> <span class="identifier">planet</span> <span class="special">=</span> <span class="identifier">hello</span><span class="special">.</span><span class="identifier">World</span><span class="special">()</span>
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">planet</span><span class="special">.</span><span class="identifier">set</span><span class="special">(</span><span class="string">'howdy'</span><span class="special">)</span> <span class="special">&gt;&gt;&gt;</span> <span class="identifier">planet</span><span class="special">.</span><span class="identifier">set</span><span class="special">(</span><span class="string">'howdy'</span><span class="special">)</span>
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">planet</span><span class="special">.</span><span class="identifier">greet</span><span class="special">()</span> <span class="special">&gt;&gt;&gt;</span> <span class="identifier">planet</span><span class="special">.</span><span class="identifier">greet</span><span class="special">()</span>
<span class="string">'howdy'</span> <span class="string">'howdy'</span>
</pre> </pre>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h3 class="title"> <div class="titlepage"><div><div><h3 class="title">
<a name="python.constructors"></a>Constructors</h3></div></div></div> <a name="python.constructors"></a>Constructors</h3></div></div></div>
<p> <p>
Our previous example didn't have any explicit constructors. Since <code class="literal">World</code> Our previous example didn't have any explicit constructors. Since <tt class="literal">World</tt>
is declared as a plain struct, it has an implicit default constructor. Boost.Python is declared as a plain struct, it has an implicit default constructor. Boost.Python
exposes the default constructor by default, which is why we were able to exposes the default constructor by default, which is why we were able to
write write
</p> </p>
<pre class="programlisting"><span class="special">&gt;&gt;&gt;</span> <span class="identifier">planet</span> <span class="special">=</span> <span class="identifier">hello</span><span class="special">.</span><span class="identifier">World</span><span class="special">()</span> <pre class="programlisting">
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">planet</span> <span class="special">=</span> <span class="identifier">hello</span><span class="special">.</span><span class="identifier">World</span><span class="special">()</span>
</pre> </pre>
<p> <p>
We may wish to wrap a class with a non-default constructor. Let us build We may wish to wrap a class with a non-default constructor. Let us build
on our previous example: on our previous example:
</p> </p>
<pre class="programlisting"><span class="keyword">struct</span> <span class="identifier">World</span> <p>
</p>
<pre class="programlisting">
<span class="keyword">struct</span> <span class="identifier">World</span>
<span class="special">{</span> <span class="special">{</span>
<span class="identifier">World</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">msg</span><span class="special">):</span> <span class="identifier">msg</span><span class="special">(</span><span class="identifier">msg</span><span class="special">)</span> <span class="special">{}</span> <span class="comment">// added constructor</span> <span class="identifier">World</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">msg</span><span class="special">):</span> <span class="identifier">msg</span><span class="special">(</span><span class="identifier">msg</span><span class="special">)</span> <span class="special">{}</span> <span class="comment">// added constructor
<span class="keyword">void</span> <span class="identifier">set</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">msg</span><span class="special">)</span> <span class="special">{</span> <span class="keyword">this</span><span class="special">-&gt;</span><span class="identifier">msg</span> <span class="special">=</span> <span class="identifier">msg</span><span class="special">;</span> <span class="special">}</span> </span> <span class="keyword">void</span> <span class="identifier">set</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">msg</span><span class="special">)</span> <span class="special">{</span> <span class="keyword">this</span><span class="special">-&gt;</span><span class="identifier">msg</span> <span class="special">=</span> <span class="identifier">msg</span><span class="special">;</span> <span class="special">}</span>
<span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">greet</span><span class="special">()</span> <span class="special">{</span> <span class="keyword">return</span> <span class="identifier">msg</span><span class="special">;</span> <span class="special">}</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">greet</span><span class="special">()</span> <span class="special">{</span> <span class="keyword">return</span> <span class="identifier">msg</span><span class="special">;</span> <span class="special">}</span>
<span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">msg</span><span class="special">;</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">msg</span><span class="special">;</span>
<span class="special">};</span> <span class="special">};</span>
</pre> </pre>
<p> <p>
This time <code class="literal">World</code> has no default constructor; our previous This time <tt class="literal">World</tt> has no default constructor; our previous
wrapping code would fail to compile when the library tried to expose it. wrapping code would fail to compile when the library tried to expose it.
We have to tell <code class="literal">class_&lt;World&gt;</code> about the constructor We have to tell <tt class="literal">class_&lt;World&gt;</tt> about the constructor
we want to expose instead. we want to expose instead.
</p> </p>
<pre class="programlisting"><span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">python</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span> <pre class="programlisting">
<span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">python</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span>
<span class="keyword">using</span> <span class="keyword">namespace</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">python</span><span class="special">;</span> <span class="keyword">using</span> <span class="keyword">namespace</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">python</span><span class="special">;</span>
<span class="identifier">BOOST_PYTHON_MODULE</span><span class="special">(</span><span class="identifier">hello</span><span class="special">)</span> <span class="identifier">BOOST_PYTHON_MODULE</span><span class="special">(</span><span class="identifier">hello</span><span class="special">)</span>
@@ -114,16 +124,17 @@
<span class="special">}</span> <span class="special">}</span>
</pre> </pre>
<p> <p>
<code class="literal">init&lt;std::string&gt;()</code> exposes the constructor taking <tt class="literal">init&lt;std::string&gt;()</tt> exposes the constructor taking
in a <code class="literal">std::string</code> (in Python, constructors are spelled in a <tt class="literal">std::string</tt> (in Python, constructors are spelled
"<code class="literal">"__init__"</code>"). "<tt class="literal">"<span class="underline">_init</span>_"</tt>").
</p> </p>
<p> <p>
We can expose additional constructors by passing more <code class="literal">init&lt;...&gt;</code>s We can expose additional constructors by passing more <tt class="literal">init&lt;...&gt;</tt>s
to the <code class="literal">def()</code> member function. Say for example we have to the <tt class="literal">def()</tt> member function. Say for example we have
another World constructor taking in two doubles: another World constructor taking in two doubles:
</p> </p>
<pre class="programlisting"><span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">World</span><span class="special">&gt;(</span><span class="string">"World"</span><span class="special">,</span> <span class="identifier">init</span><span class="special">&lt;</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span><span class="special">&gt;())</span> <pre class="programlisting">
<span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">World</span><span class="special">&gt;(</span><span class="string">"World"</span><span class="special">,</span> <span class="identifier">init</span><span class="special">&lt;</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span><span class="special">&gt;())</span>
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">init</span><span class="special">&lt;</span><span class="keyword">double</span><span class="special">,</span> <span class="keyword">double</span><span class="special">&gt;())</span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">init</span><span class="special">&lt;</span><span class="keyword">double</span><span class="special">,</span> <span class="keyword">double</span><span class="special">&gt;())</span>
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"greet"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">World</span><span class="special">::</span><span class="identifier">greet</span><span class="special">)</span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"greet"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">World</span><span class="special">::</span><span class="identifier">greet</span><span class="special">)</span>
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"set"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">World</span><span class="special">::</span><span class="identifier">set</span><span class="special">)</span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"set"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">World</span><span class="special">::</span><span class="identifier">set</span><span class="special">)</span>
@@ -131,25 +142,27 @@
</pre> </pre>
<p> <p>
On the other hand, if we do not wish to expose any constructors at all, we On the other hand, if we do not wish to expose any constructors at all, we
may use <code class="literal">no_init</code> instead: may use <tt class="literal">no_init</tt> instead:
</p> </p>
<pre class="programlisting"><span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">Abstract</span><span class="special">&gt;(</span><span class="string">"Abstract"</span><span class="special">,</span> <span class="identifier">no_init</span><span class="special">)</span> <pre class="programlisting">
<span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">Abstract</span><span class="special">&gt;(</span><span class="string">"Abstract"</span><span class="special">,</span> <span class="identifier">no_init</span><span class="special">)</span>
</pre> </pre>
<p> <p>
This actually adds an <code class="literal">__init__</code> method which always raises This actually adds an <tt class="literal"><span class="underline">_init</span>_</tt>
a Python RuntimeError exception. method which always raises a Python RuntimeError exception.
</p> </p>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h3 class="title"> <div class="titlepage"><div><div><h3 class="title">
<a name="python.class_data_members"></a>Class Data Members</h3></div></div></div> <a name="python.class_data_members"></a>Class Data Members</h3></div></div></div>
<p> <p>
Data members may also be exposed to Python so that they can be accessed as Data members may also be exposed to Python so that they can be accessed as
attributes of the corresponding Python class. Each data member that we wish attributes of the corresponding Python class. Each data member that we wish
to be exposed may be regarded as <span class="bold"><strong>read-only</strong></span> to be exposed may be regarded as <span class="bold"><b>read-only</b></span>
or <span class="bold"><strong>read-write</strong></span>. Consider this class <code class="literal">Var</code>: or <span class="bold"><b>read-write</b></span>. Consider this class <tt class="literal">Var</tt>:
</p> </p>
<pre class="programlisting"><span class="keyword">struct</span> <span class="identifier">Var</span> <pre class="programlisting">
<span class="keyword">struct</span> <span class="identifier">Var</span>
<span class="special">{</span> <span class="special">{</span>
<span class="identifier">Var</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">name</span><span class="special">)</span> <span class="special">:</span> <span class="identifier">name</span><span class="special">(</span><span class="identifier">name</span><span class="special">),</span> <span class="identifier">value</span><span class="special">()</span> <span class="special">{}</span> <span class="identifier">Var</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">name</span><span class="special">)</span> <span class="special">:</span> <span class="identifier">name</span><span class="special">(</span><span class="identifier">name</span><span class="special">),</span> <span class="identifier">value</span><span class="special">()</span> <span class="special">{}</span>
<span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="keyword">const</span> <span class="identifier">name</span><span class="special">;</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="keyword">const</span> <span class="identifier">name</span><span class="special">;</span>
@@ -157,10 +170,11 @@
<span class="special">};</span> <span class="special">};</span>
</pre> </pre>
<p> <p>
Our C++ <code class="literal">Var</code> class and its data members can be exposed Our C++ <tt class="literal">Var</tt> class and its data members can be exposed
to Python: to Python:
</p> </p>
<pre class="programlisting"><span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">Var</span><span class="special">&gt;(</span><span class="string">"Var"</span><span class="special">,</span> <span class="identifier">init</span><span class="special">&lt;</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span><span class="special">&gt;())</span> <pre class="programlisting">
<span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">Var</span><span class="special">&gt;(</span><span class="string">"Var"</span><span class="special">,</span> <span class="identifier">init</span><span class="special">&lt;</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span><span class="special">&gt;())</span>
<span class="special">.</span><span class="identifier">def_readonly</span><span class="special">(</span><span class="string">"name"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">Var</span><span class="special">::</span><span class="identifier">name</span><span class="special">)</span> <span class="special">.</span><span class="identifier">def_readonly</span><span class="special">(</span><span class="string">"name"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">Var</span><span class="special">::</span><span class="identifier">name</span><span class="special">)</span>
<span class="special">.</span><span class="identifier">def_readwrite</span><span class="special">(</span><span class="string">"value"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">Var</span><span class="special">::</span><span class="identifier">value</span><span class="special">);</span> <span class="special">.</span><span class="identifier">def_readwrite</span><span class="special">(</span><span class="string">"value"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">Var</span><span class="special">::</span><span class="identifier">value</span><span class="special">);</span>
</pre> </pre>
@@ -168,22 +182,26 @@
Then, in Python, assuming we have placed our Var class inside the namespace Then, in Python, assuming we have placed our Var class inside the namespace
hello as we did before: hello as we did before:
</p> </p>
<pre class="programlisting"><span class="special">&gt;&gt;&gt;</span> <span class="identifier">x</span> <span class="special">=</span> <span class="identifier">hello</span><span class="special">.</span><span class="identifier">Var</span><span class="special">(</span><span class="string">'pi'</span><span class="special">)</span> <p>
</p>
<pre class="programlisting">
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">x</span> <span class="special">=</span> <span class="identifier">hello</span><span class="special">.</span><span class="identifier">Var</span><span class="special">(</span><span class="string">'pi'</span><span class="special">)</span>
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">value</span> <span class="special">=</span> <span class="number">3.14</span> <span class="special">&gt;&gt;&gt;</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">value</span> <span class="special">=</span> <span class="number">3.14</span>
<span class="special">&gt;&gt;&gt;</span> <span class="keyword">print</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">name</span><span class="special">,</span> <span class="string">'is around'</span><span class="special">,</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">value</span> <span class="special">&gt;&gt;&gt;</span> <span class="keyword">print</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">name</span><span class="special">,</span> <span class="string">'is around'</span><span class="special">,</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">value</span>
<span class="identifier">pi</span> <span class="keyword">is</span> <span class="identifier">around</span> <span class="number">3.14</span> <span class="identifier">pi</span> <span class="keyword">is</span> <span class="identifier">around</span> <span class="number">3.14</span>
</pre> </pre>
<p> <p>
Note that <code class="literal">name</code> is exposed as <span class="bold"><strong>read-only</strong></span> Note that <tt class="literal">name</tt> is exposed as <span class="bold"><b>read-only</b></span>
while <code class="literal">value</code> is exposed as <span class="bold"><strong>read-write</strong></span>. while <tt class="literal">value</tt> is exposed as <span class="bold"><b>read-write</b></span>.
</p> </p>
<pre class="programlisting"><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="string">'e'</span> <span class="comment"># can't change name</span> <pre class="programlisting">
<span class="identifier">Traceback</span> <span class="special">(</span><span class="identifier">most</span> <span class="identifier">recent</span> <span class="identifier">call</span> <span class="identifier">last</span><span class="special">):</span> <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="string">'e'</span> <span class="comment"># can't change name
<span class="identifier">File</span> <span class="string">"&lt;stdin&gt;"</span><span class="special">,</span> <span class="identifier">line</span> <span class="number">1</span><span class="special">,</span> <span class="keyword">in</span> <span class="error">?</span> </span><span class="identifier">Traceback</span> <span class="special">(</span><span class="identifier">most</span> <span class="identifier">recent</span> <span class="identifier">call</span> <span class="identifier">last</span><span class="special">):</span>
<span class="identifier">AttributeError</span><span class="special">:</span> <span class="identifier">can</span><span class="error">'</span><span class="identifier">t</span> <span class="identifier">set</span> <span class="identifier">attribute</span> <span class="identifier">File</span> <span class="string">"&lt;stdin&gt;"</span><span class="special">,</span> <span class="identifier">line</span> <span class="number">1</span><span class="special">,</span> <span class="keyword">in</span> #
<span class="identifier">AttributeError</span><span class="special">:</span> <span class="identifier">can</span>#<span class="identifier">t</span> <span class="identifier">set</span> <span class="identifier">attribute</span>
</pre> </pre>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h3 class="title"> <div class="titlepage"><div><div><h3 class="title">
<a name="python.class_properties"></a>Class Properties</h3></div></div></div> <a name="python.class_properties"></a>Class Properties</h3></div></div></div>
<p> <p>
@@ -192,7 +210,10 @@
The only way to access the class' data is through access (getter/setter) The only way to access the class' data is through access (getter/setter)
functions. Access functions expose class properties. Here's an example: functions. Access functions expose class properties. Here's an example:
</p> </p>
<pre class="programlisting"><span class="keyword">struct</span> <span class="identifier">Num</span> <p>
</p>
<pre class="programlisting">
<span class="keyword">struct</span> <span class="identifier">Num</span>
<span class="special">{</span> <span class="special">{</span>
<span class="identifier">Num</span><span class="special">();</span> <span class="identifier">Num</span><span class="special">();</span>
<span class="keyword">float</span> <span class="identifier">get</span><span class="special">()</span> <span class="keyword">const</span><span class="special">;</span> <span class="keyword">float</span> <span class="identifier">get</span><span class="special">()</span> <span class="keyword">const</span><span class="special">;</span>
@@ -203,31 +224,38 @@
<p> <p>
However, in Python attribute access is fine; it doesn't neccessarily break However, in Python attribute access is fine; it doesn't neccessarily break
encapsulation to let users handle attributes directly, because the attributes encapsulation to let users handle attributes directly, because the attributes
can just be a different syntax for a method call. Wrapping our <code class="literal">Num</code> can just be a different syntax for a method call. Wrapping our <tt class="literal">Num</tt>
class using Boost.Python: class using Boost.Python:
</p> </p>
<pre class="programlisting"><span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">Num</span><span class="special">&gt;(</span><span class="string">"Num"</span><span class="special">)</span> <pre class="programlisting">
<span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">Num</span><span class="special">&gt;(</span><span class="string">"Num"</span><span class="special">)</span>
<span class="special">.</span><span class="identifier">add_property</span><span class="special">(</span><span class="string">"rovalue"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">Num</span><span class="special">::</span><span class="identifier">get</span><span class="special">)</span> <span class="special">.</span><span class="identifier">add_property</span><span class="special">(</span><span class="string">"rovalue"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">Num</span><span class="special">::</span><span class="identifier">get</span><span class="special">)</span>
<span class="special">.</span><span class="identifier">add_property</span><span class="special">(</span><span class="string">"value"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">Num</span><span class="special">::</span><span class="identifier">get</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">Num</span><span class="special">::</span><span class="identifier">set</span><span class="special">);</span> <span class="special">.</span><span class="identifier">add_property</span><span class="special">(</span><span class="string">"value"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">Num</span><span class="special">::</span><span class="identifier">get</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">Num</span><span class="special">::</span><span class="identifier">set</span><span class="special">);</span>
</pre> </pre>
<p> <p>
And at last, in Python: And at last, in Python:
</p> </p>
<pre class="programlisting"><span class="special">&gt;&gt;&gt;</span> <span class="identifier">x</span> <span class="special">=</span> <span class="identifier">Num</span><span class="special">()</span> <p>
</p>
<pre class="programlisting">
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">x</span> <span class="special">=</span> <span class="identifier">Num</span><span class="special">()</span>
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">value</span> <span class="special">=</span> <span class="number">3.14</span> <span class="special">&gt;&gt;&gt;</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">value</span> <span class="special">=</span> <span class="number">3.14</span>
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">value</span><span class="special">,</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">rovalue</span> <span class="special">&gt;&gt;&gt;</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">value</span><span class="special">,</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">rovalue</span>
<span class="special">(</span><span class="number">3.14</span><span class="special">,</span> <span class="number">3.14</span><span class="special">)</span> <span class="special">(</span><span class="number">3.14</span><span class="special">,</span> <span class="number">3.14</span><span class="special">)</span>
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">rovalue</span> <span class="special">=</span> <span class="number">2.17</span> <span class="comment"># error!</span> <span class="special">&gt;&gt;&gt;</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">rovalue</span> <span class="special">=</span> <span class="number">2.17</span> <span class="comment"># error!
</pre> </span></pre>
<p> <p>
Take note that the class property <code class="literal">rovalue</code> is exposed as Take note that the class property <tt class="literal">rovalue</tt> is exposed as
<span class="bold"><strong>read-only</strong></span> since the <code class="literal">rovalue</code> <span class="bold"><b>read-only</b></span> since the <tt class="literal">rovalue</tt>
setter member function is not passed in: setter member function is not passed in:
</p> </p>
<pre class="programlisting"><span class="special">.</span><span class="identifier">add_property</span><span class="special">(</span><span class="string">"rovalue"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">Num</span><span class="special">::</span><span class="identifier">get</span><span class="special">)</span> <p>
</p>
<pre class="programlisting">
<span class="special">.</span><span class="identifier">add_property</span><span class="special">(</span><span class="string">"rovalue"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">Num</span><span class="special">::</span><span class="identifier">get</span><span class="special">)</span>
</pre> </pre>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h3 class="title"> <div class="titlepage"><div><div><h3 class="title">
<a name="python.inheritance"></a>Inheritance</h3></div></div></div> <a name="python.inheritance"></a>Inheritance</h3></div></div></div>
<p> <p>
@@ -240,78 +268,85 @@
<p> <p>
Consider this trivial inheritance structure: Consider this trivial inheritance structure:
</p> </p>
<pre class="programlisting"><span class="keyword">struct</span> <span class="identifier">Base</span> <span class="special">{</span> <span class="keyword">virtual</span> <span class="special">~</span><span class="identifier">Base</span><span class="special">();</span> <span class="special">};</span> <pre class="programlisting">
<span class="keyword">struct</span> <span class="identifier">Base</span> <span class="special">{</span> <span class="keyword">virtual</span> <span class="special">~</span><span class="identifier">Base</span><span class="special">();</span> <span class="special">};</span>
<span class="keyword">struct</span> <span class="identifier">Derived</span> <span class="special">:</span> <span class="identifier">Base</span> <span class="special">{};</span> <span class="keyword">struct</span> <span class="identifier">Derived</span> <span class="special">:</span> <span class="identifier">Base</span> <span class="special">{};</span>
</pre> </pre>
<p> <p>
And a set of C++ functions operating on <code class="literal">Base</code> and <code class="literal">Derived</code> And a set of C++ functions operating on <tt class="literal">Base</tt> and <tt class="literal">Derived</tt>
object instances: object instances:
</p> </p>
<pre class="programlisting"><span class="keyword">void</span> <span class="identifier">b</span><span class="special">(</span><span class="identifier">Base</span><span class="special">*);</span> <pre class="programlisting">
<span class="keyword">void</span> <span class="identifier">b</span><span class="special">(</span><span class="identifier">Base</span><span class="special">*);</span>
<span class="keyword">void</span> <span class="identifier">d</span><span class="special">(</span><span class="identifier">Derived</span><span class="special">*);</span> <span class="keyword">void</span> <span class="identifier">d</span><span class="special">(</span><span class="identifier">Derived</span><span class="special">*);</span>
<span class="identifier">Base</span><span class="special">*</span> <span class="identifier">factory</span><span class="special">()</span> <span class="special">{</span> <span class="keyword">return</span> <span class="keyword">new</span> <span class="identifier">Derived</span><span class="special">;</span> <span class="special">}</span> <span class="identifier">Base</span><span class="special">*</span> <span class="identifier">factory</span><span class="special">()</span> <span class="special">{</span> <span class="keyword">return</span> <span class="keyword">new</span> <span class="identifier">Derived</span><span class="special">;</span> <span class="special">}</span>
</pre> </pre>
<p> <p>
We've seen how we can wrap the base class <code class="literal">Base</code>: We've seen how we can wrap the base class <tt class="literal">Base</tt>:
</p> </p>
<pre class="programlisting"><span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">Base</span><span class="special">&gt;(</span><span class="string">"Base"</span><span class="special">)</span> <pre class="programlisting">
<span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">Base</span><span class="special">&gt;(</span><span class="string">"Base"</span><span class="special">)</span>
<span class="comment">/*...*/</span> <span class="comment">/*...*/</span>
<span class="special">;</span> <span class="special">;</span>
</pre> </pre>
<p> <p>
Now we can inform Boost.Python of the inheritance relationship between <code class="literal">Derived</code> Now we can inform Boost.Python of the inheritance relationship between <tt class="literal">Derived</tt>
and its base class <code class="literal">Base</code>. Thus: and its base class <tt class="literal">Base</tt>. Thus:
</p> </p>
<pre class="programlisting"><span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">Derived</span><span class="special">,</span> <span class="identifier">bases</span><span class="special">&lt;</span><span class="identifier">Base</span><span class="special">&gt;</span> <span class="special">&gt;(</span><span class="string">"Derived"</span><span class="special">)</span> <pre class="programlisting">
<span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">Derived</span><span class="special">,</span> <span class="identifier">bases</span><span class="special">&lt;</span><span class="identifier">Base</span><span class="special">&gt;</span> <span class="special">&gt;(</span><span class="string">"Derived"</span><span class="special">)</span>
<span class="comment">/*...*/</span> <span class="comment">/*...*/</span>
<span class="special">;</span> <span class="special">;</span>
</pre> </pre>
<p> <p>
Doing so, we get some things for free: Doing so, we get some things for free:
</p> </p>
<div class="orderedlist"><ol class="orderedlist" type="1"> <div class="orderedlist"><ol type="1">
<li class="listitem"> <li>
Derived automatically inherits all of Base's Python methods (wrapped Derived automatically inherits all of Base's Python methods (wrapped C++
C++ member functions) member functions)
</li> </li>
<li class="listitem"> <li>
<span class="bold"><strong>If</strong></span> Base is polymorphic, <code class="literal">Derived</code> <span class="bold"><b>If</b></span> Base is polymorphic, <tt class="literal">Derived</tt>
objects which have been passed to Python via a pointer or reference to objects which have been passed to Python via a pointer or reference to
<code class="literal">Base</code> can be passed where a pointer or reference to <tt class="literal">Base</tt> can be passed where a pointer or reference to
<code class="literal">Derived</code> is expected. <tt class="literal">Derived</tt> is expected.
</li> </li>
</ol></div> </ol></div>
<p> <p>
Now, we will expose the C++ free functions <code class="literal">b</code> and <code class="literal">d</code> Now, we will expose the C++ free functions <tt class="literal">b</tt> and <tt class="literal">d</tt>
and <code class="literal">factory</code>: and <tt class="literal">factory</tt>:
</p> </p>
<pre class="programlisting"><span class="identifier">def</span><span class="special">(</span><span class="string">"b"</span><span class="special">,</span> <span class="identifier">b</span><span class="special">);</span> <pre class="programlisting">
<span class="identifier">def</span><span class="special">(</span><span class="string">"b"</span><span class="special">,</span> <span class="identifier">b</span><span class="special">);</span>
<span class="identifier">def</span><span class="special">(</span><span class="string">"d"</span><span class="special">,</span> <span class="identifier">d</span><span class="special">);</span> <span class="identifier">def</span><span class="special">(</span><span class="string">"d"</span><span class="special">,</span> <span class="identifier">d</span><span class="special">);</span>
<span class="identifier">def</span><span class="special">(</span><span class="string">"factory"</span><span class="special">,</span> <span class="identifier">factory</span><span class="special">);</span> <span class="identifier">def</span><span class="special">(</span><span class="string">"factory"</span><span class="special">,</span> <span class="identifier">factory</span><span class="special">);</span>
</pre> </pre>
<p> <p>
Note that free function <code class="literal">factory</code> is being used to generate Note that free function <tt class="literal">factory</tt> is being used to generate
new instances of class <code class="literal">Derived</code>. In such cases, we use new instances of class <tt class="literal">Derived</tt>. In such cases, we use
<code class="literal">return_value_policy&lt;manage_new_object&gt;</code> to instruct <tt class="literal">return_value_policy&lt;manage_new_object&gt;</tt> to instruct
Python to adopt the pointer to <code class="literal">Base</code> and hold the instance Python to adopt the pointer to <tt class="literal">Base</tt> and hold the instance
in a new Python <code class="literal">Base</code> object until the the Python object in a new Python <tt class="literal">Base</tt> object until the the Python object
is destroyed. We will see more of Boost.Python <a class="link" href="functions.html#python.call_policies" title="Call Policies">call is destroyed. We will see more of Boost.Python <a href="functions.html#python.call_policies" title="Call Policies">call
policies</a> later. policies</a> later.
</p> </p>
<pre class="programlisting"><span class="comment">// Tell Python to take ownership of factory's result</span> <pre class="programlisting">
<span class="identifier">def</span><span class="special">(</span><span class="string">"factory"</span><span class="special">,</span> <span class="identifier">factory</span><span class="special">,</span> <span class="comment">// Tell Python to take ownership of factory's result
</span><span class="identifier">def</span><span class="special">(</span><span class="string">"factory"</span><span class="special">,</span> <span class="identifier">factory</span><span class="special">,</span>
<span class="identifier">return_value_policy</span><span class="special">&lt;</span><span class="identifier">manage_new_object</span><span class="special">&gt;());</span> <span class="identifier">return_value_policy</span><span class="special">&lt;</span><span class="identifier">manage_new_object</span><span class="special">&gt;());</span>
</pre> </pre>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h3 class="title"> <div class="titlepage"><div><div><h3 class="title">
<a name="python.class_virtual_functions"></a>Class Virtual Functions</h3></div></div></div> <a name="python.class_virtual_functions"></a>Class Virtual Functions</h3></div></div></div>
<p> <p>
In this section, we will learn how to make functions behave polymorphically In this section, we will learn how to make functions behave polymorphically
through virtual functions. Continuing our example, let us add a virtual function through virtual functions. Continuing our example, let us add a virtual function
to our <code class="literal">Base</code> class: to our <tt class="literal">Base</tt> class:
</p> </p>
<pre class="programlisting"><span class="keyword">struct</span> <span class="identifier">Base</span> <pre class="programlisting">
<span class="keyword">struct</span> <span class="identifier">Base</span>
<span class="special">{</span> <span class="special">{</span>
<span class="keyword">virtual</span> <span class="special">~</span><span class="identifier">Base</span><span class="special">()</span> <span class="special">{}</span> <span class="keyword">virtual</span> <span class="special">~</span><span class="identifier">Base</span><span class="special">()</span> <span class="special">{}</span>
<span class="keyword">virtual</span> <span class="keyword">int</span> <span class="identifier">f</span><span class="special">()</span> <span class="special">=</span> <span class="number">0</span><span class="special">;</span> <span class="keyword">virtual</span> <span class="keyword">int</span> <span class="identifier">f</span><span class="special">()</span> <span class="special">=</span> <span class="number">0</span><span class="special">;</span>
@@ -321,15 +356,16 @@
One of the goals of Boost.Python is to be minimally intrusive on an existing One of the goals of Boost.Python is to be minimally intrusive on an existing
C++ design. In principle, it should be possible to expose the interface for C++ design. In principle, it should be possible to expose the interface for
a 3rd party library without changing it. It is not ideal to add anything a 3rd party library without changing it. It is not ideal to add anything
to our class <code class="computeroutput"><span class="identifier">Base</span></code>. Yet, when to our class <tt class="computeroutput"><span class="identifier">Base</span></tt>. Yet, when
you have a virtual function that's going to be overridden in Python and called you have a virtual function that's going to be overridden in Python and called
polymorphically <span class="bold"><strong>from C++</strong></span>, we'll need to polymorphically <span class="bold"><b>from C++</b></span>, we'll need to
add some scaffoldings to make things work properly. What we'll do is write add some scaffoldings to make things work properly. What we'll do is write
a class wrapper that derives from <code class="computeroutput"><span class="identifier">Base</span></code> a class wrapper that derives from <tt class="computeroutput"><span class="identifier">Base</span></tt>
that will unintrusively hook into the virtual functions so that a Python that will unintrusively hook into the virtual functions so that a Python
override may be called: override may be called:
</p> </p>
<pre class="programlisting"><span class="keyword">struct</span> <span class="identifier">BaseWrap</span> <span class="special">:</span> <span class="identifier">Base</span><span class="special">,</span> <span class="identifier">wrapper</span><span class="special">&lt;</span><span class="identifier">Base</span><span class="special">&gt;</span> <pre class="programlisting">
<span class="keyword">struct</span> <span class="identifier">BaseWrap</span> <span class="special">:</span> <span class="identifier">Base</span><span class="special">,</span> <span class="identifier">wrapper</span><span class="special">&lt;</span><span class="identifier">Base</span><span class="special">&gt;</span>
<span class="special">{</span> <span class="special">{</span>
<span class="keyword">int</span> <span class="identifier">f</span><span class="special">()</span> <span class="keyword">int</span> <span class="identifier">f</span><span class="special">()</span>
<span class="special">{</span> <span class="special">{</span>
@@ -338,79 +374,81 @@
<span class="special">};</span> <span class="special">};</span>
</pre> </pre>
<p> <p>
Notice too that in addition to inheriting from <code class="computeroutput"><span class="identifier">Base</span></code>, Notice too that in addition to inheriting from <tt class="computeroutput"><span class="identifier">Base</span></tt>,
we also multiply- inherited <code class="computeroutput"><span class="identifier">wrapper</span><span class="special">&lt;</span><span class="identifier">Base</span><span class="special">&gt;</span></code> (See <a href="../../../../v2/wrapper.html" target="_top">Wrapper</a>). we also multiply- inherited <tt class="computeroutput"><span class="identifier">wrapper</span><span class="special">&lt;</span><span class="identifier">Base</span><span class="special">&gt;</span></tt> (See <a href="../../../../v2/wrapper.html" target="_top">Wrapper</a>).
The <code class="computeroutput"><span class="identifier">wrapper</span></code> template makes The <tt class="computeroutput"><span class="identifier">wrapper</span></tt> template makes
the job of wrapping classes that are meant to overridden in Python, easier. the job of wrapping classes that are meant to overridden in Python, easier.
</p> </p>
<div class="sidebar"> <div class="sidebar">
<div class="titlepage"></div>
<p> <p>
<span class="inlinemediaobject"><img src="../images/alert.png" alt="alert"></span> <span class="bold"><strong>MSVC6/7 Workaround</strong></span> <span class="inlinemediaobject"><img src="../images/alert.png" alt="alert"></span> <span class="bold"><b>MSVC6/7 Workaround</b></span>
</p> </p>
<p> <p>
If you are using Microsoft Visual C++ 6 or 7, you have to write <code class="computeroutput"><span class="identifier">f</span></code> as: If you are using Microsoft Visual C++ 6 or 7, you have to write <tt class="computeroutput"><span class="identifier">f</span></tt> as:
</p> </p>
<p> <p>
<code class="computeroutput"><span class="keyword">return</span> <span class="identifier">call</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;(</span><span class="keyword">this</span><span class="special">-&gt;</span><span class="identifier">get_override</span><span class="special">(</span><span class="string">"f"</span><span class="special">).</span><span class="identifier">ptr</span><span class="special">());</span></code>. <tt class="computeroutput"><span class="keyword">return</span> <span class="identifier">call</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;(</span><span class="keyword">this</span><span class="special">-&gt;</span><span class="identifier">get_override</span><span class="special">(</span><span class="string">"f"</span><span class="special">).</span><span class="identifier">ptr</span><span class="special">());</span></tt>.
</p> </p>
</div> </div>
<p> <p>
BaseWrap's overridden virtual member function <code class="computeroutput"><span class="identifier">f</span></code> BaseWrap's overridden virtual member function <tt class="computeroutput"><span class="identifier">f</span></tt>
in effect calls the corresponding method of the Python object through <code class="computeroutput"><span class="identifier">get_override</span></code>. in effect calls the corresponding method of the Python object through <tt class="computeroutput"><span class="identifier">get_override</span></tt>.
</p> </p>
<p> <p>
Finally, exposing <code class="computeroutput"><span class="identifier">Base</span></code>: Finally, exposing <tt class="computeroutput"><span class="identifier">Base</span></tt>:
</p> </p>
<pre class="programlisting"><span class="identifier">class_</span><span class="special">&lt;</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">"Base"</span><span class="special">)</span> <pre class="programlisting">
<span class="identifier">class_</span><span class="special">&lt;</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">"Base"</span><span class="special">)</span>
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">pure_virtual</span><span class="special">(&amp;</span><span class="identifier">Base</span><span class="special">::</span><span class="identifier">f</span><span class="special">))</span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">pure_virtual</span><span class="special">(&amp;</span><span class="identifier">Base</span><span class="special">::</span><span class="identifier">f</span><span class="special">))</span>
<span class="special">;</span> <span class="special">;</span>
</pre> </pre>
<p> <p>
<code class="computeroutput"><span class="identifier">pure_virtual</span></code> signals Boost.Python <tt class="computeroutput"><span class="identifier">pure_virtual</span></tt> signals Boost.Python
that the function <code class="computeroutput"><span class="identifier">f</span></code> is a that the function <tt class="computeroutput"><span class="identifier">f</span></tt> is a
pure virtual function. pure virtual function.
</p> </p>
<div class="note"><table border="0" summary="Note"> <div class="note"><table border="0" summary="Note">
<tr> <tr>
<td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../../../doc/src/images/note.png"></td> <td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../../../doc/html/images/note.png"></td>
<th align="left">Note</th> <th align="left">Note</th>
</tr> </tr>
<tr><td align="left" valign="top"> <tr><td colspan="2" align="left" valign="top">
<p> <p>
<span class="bold"><strong>member function and methods</strong></span> <span class="bold"><b>member function and methods</b></span>
</p> </p>
<p> <p>
Python, like many object oriented languages uses the term <span class="bold"><strong>methods</strong></span>. Python, like many object oriented languages uses the term <span class="bold"><b>methods</b></span>.
Methods correspond roughly to C++'s <span class="bold"><strong>member functions</strong></span> Methods correspond roughly to C++'s <span class="bold"><b>member functions</b></span>
</p> </p>
</td></tr> </td></tr>
</table></div> </table></div>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h3 class="title"> <div class="titlepage"><div><div><h3 class="title">
<a name="python.virtual_functions_with_default_implementations"></a>Virtual Functions with Default Implementations</h3></div></div></div> <a name="python.virtual_functions_with_default_implementations"></a>Virtual Functions with Default Implementations</h3></div></div></div>
<p> <p>
We've seen in the previous section how classes with pure virtual functions We've seen in the previous section how classes with pure virtual functions
are wrapped using Boost.Python's <a href="../../../../v2/wrapper.html" target="_top">class are wrapped using Boost.Python's <a href="../../../../v2/wrapper.html" target="_top">class
wrapper</a> facilities. If we wish to wrap <span class="bold"><strong>non</strong></span>-pure-virtual wrapper</a> facilities. If we wish to wrap <span class="bold"><b>non</b></span>-pure-virtual
functions instead, the mechanism is a bit different. functions instead, the mechanism is a bit different.
</p> </p>
<p> <p>
Recall that in the <a class="link" href="exposing.html#python.class_virtual_functions" title="Class Virtual Functions">previous Recall that in the <a href="exposing.html#python.class_virtual_functions" title="Class Virtual Functions">previous
section</a>, we wrapped a class with a pure virtual function that we then section</a>, we wrapped a class with a pure virtual function that we then
implemented in C++, or Python classes derived from it. Our base class: implemented in C++, or Python classes derived from it. Our base class:
</p> </p>
<pre class="programlisting"><span class="keyword">struct</span> <span class="identifier">Base</span> <pre class="programlisting">
<span class="keyword">struct</span> <span class="identifier">Base</span>
<span class="special">{</span> <span class="special">{</span>
<span class="keyword">virtual</span> <span class="keyword">int</span> <span class="identifier">f</span><span class="special">()</span> <span class="special">=</span> <span class="number">0</span><span class="special">;</span> <span class="keyword">virtual</span> <span class="keyword">int</span> <span class="identifier">f</span><span class="special">()</span> <span class="special">=</span> <span class="number">0</span><span class="special">;</span>
<span class="special">};</span> <span class="special">};</span>
</pre> </pre>
<p> <p>
had a pure virtual function <code class="literal">f</code>. If, however, its member had a pure virtual function <tt class="literal">f</tt>. If, however, its member
function <code class="literal">f</code> was not declared as pure virtual: function <tt class="literal">f</tt> was not declared as pure virtual:
</p> </p>
<pre class="programlisting"><span class="keyword">struct</span> <span class="identifier">Base</span> <pre class="programlisting">
<span class="keyword">struct</span> <span class="identifier">Base</span>
<span class="special">{</span> <span class="special">{</span>
<span class="keyword">virtual</span> <span class="special">~</span><span class="identifier">Base</span><span class="special">()</span> <span class="special">{}</span> <span class="keyword">virtual</span> <span class="special">~</span><span class="identifier">Base</span><span class="special">()</span> <span class="special">{}</span>
<span class="keyword">virtual</span> <span class="keyword">int</span> <span class="identifier">f</span><span class="special">()</span> <span class="special">{</span> <span class="keyword">return</span> <span class="number">0</span><span class="special">;</span> <span class="special">}</span> <span class="keyword">virtual</span> <span class="keyword">int</span> <span class="identifier">f</span><span class="special">()</span> <span class="special">{</span> <span class="keyword">return</span> <span class="number">0</span><span class="special">;</span> <span class="special">}</span>
@@ -419,53 +457,57 @@
<p> <p>
We wrap it this way: We wrap it this way:
</p> </p>
<pre class="programlisting"><span class="keyword">struct</span> <span class="identifier">BaseWrap</span> <span class="special">:</span> <span class="identifier">Base</span><span class="special">,</span> <span class="identifier">wrapper</span><span class="special">&lt;</span><span class="identifier">Base</span><span class="special">&gt;</span> <pre class="programlisting">
<span class="keyword">struct</span> <span class="identifier">BaseWrap</span> <span class="special">:</span> <span class="identifier">Base</span><span class="special">,</span> <span class="identifier">wrapper</span><span class="special">&lt;</span><span class="identifier">Base</span><span class="special">&gt;</span>
<span class="special">{</span> <span class="special">{</span>
<span class="keyword">int</span> <span class="identifier">f</span><span class="special">()</span> <span class="keyword">int</span> <span class="identifier">f</span><span class="special">()</span>
<span class="special">{</span> <span class="special">{</span>
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">override</span> <span class="identifier">f</span> <span class="special">=</span> <span class="keyword">this</span><span class="special">-&gt;</span><span class="identifier">get_override</span><span class="special">(</span><span class="string">"f"</span><span class="special">))</span> <span class="keyword">if</span> <span class="special">(</span><span class="identifier">override</span> <span class="identifier">f</span> <span class="special">=</span> <span class="keyword">this</span><span class="special">-&gt;</span><span class="identifier">get_override</span><span class="special">(</span><span class="string">"f"</span><span class="special">))</span>
<span class="keyword">return</span> <span class="identifier">f</span><span class="special">();</span> <span class="comment">// *note*</span> <span class="keyword">return</span> <span class="identifier">f</span><span class="special">();</span> <span class="comment">// *note*
<span class="keyword">return</span> <span class="identifier">Base</span><span class="special">::</span><span class="identifier">f</span><span class="special">();</span> </span> <span class="keyword">return</span> <span class="identifier">Base</span><span class="special">::</span><span class="identifier">f</span><span class="special">();</span>
<span class="special">}</span> <span class="special">}</span>
<span class="keyword">int</span> <span class="identifier">default_f</span><span class="special">()</span> <span class="special">{</span> <span class="keyword">return</span> <span class="keyword">this</span><span class="special">-&gt;</span><span class="identifier">Base</span><span class="special">::</span><span class="identifier">f</span><span class="special">();</span> <span class="special">}</span> <span class="keyword">int</span> <span class="identifier">default_f</span><span class="special">()</span> <span class="special">{</span> <span class="keyword">return</span> <span class="keyword">this</span><span class="special">-&gt;</span><span class="identifier">Base</span><span class="special">::</span><span class="identifier">f</span><span class="special">();</span> <span class="special">}</span>
<span class="special">};</span> <span class="special">};</span>
</pre> </pre>
<p> <p>
Notice how we implemented <code class="computeroutput"><span class="identifier">BaseWrap</span><span class="special">::</span><span class="identifier">f</span></code>. Now, Notice how we implemented <tt class="computeroutput"><span class="identifier">BaseWrap</span><span class="special">::</span><span class="identifier">f</span></tt>. Now,
we have to check if there is an override for <code class="computeroutput"><span class="identifier">f</span></code>. we have to check if there is an override for <tt class="computeroutput"><span class="identifier">f</span></tt>.
If none, then we call <code class="computeroutput"><span class="identifier">Base</span><span class="special">::</span><span class="identifier">f</span><span class="special">()</span></code>. If none, then we call <tt class="computeroutput"><span class="identifier">Base</span><span class="special">::</span><span class="identifier">f</span><span class="special">()</span></tt>.
</p> </p>
<div class="sidebar"> <div class="sidebar">
<div class="titlepage"></div>
<p> <p>
<span class="inlinemediaobject"><img src="../images/alert.png" alt="alert"></span> <span class="bold"><strong>MSVC6/7 Workaround</strong></span> <span class="inlinemediaobject"><img src="../images/alert.png" alt="alert"></span> <span class="bold"><b>MSVC6/7 Workaround</b></span>
</p> </p>
<p> <p>
If you are using Microsoft Visual C++ 6 or 7, you have to rewrite the line If you are using Microsoft Visual C++ 6 or 7, you have to rewrite the line
with the <code class="computeroutput"><span class="special">*</span><span class="identifier">note</span><span class="special">*</span></code> as: with the <tt class="computeroutput"><span class="special">*</span><span class="identifier">note</span><span class="special">*</span></tt> as:
</p> </p>
<p> <p>
<code class="computeroutput"><span class="keyword">return</span> <span class="identifier">call</span><span class="special">&lt;</span><span class="keyword">char</span> <span class="keyword">const</span><span class="special">*&gt;(</span><span class="identifier">f</span><span class="special">.</span><span class="identifier">ptr</span><span class="special">());</span></code>. <tt class="computeroutput"><span class="keyword">return</span> <span class="identifier">call</span><span class="special">&lt;</span><span class="keyword">char</span> <span class="keyword">const</span><span class="special">*&gt;(</span><span class="identifier">f</span><span class="special">.</span><span class="identifier">ptr</span><span class="special">());</span></tt>.
</p> </p>
</div> </div>
<p> <p>
Finally, exposing: Finally, exposing:
</p> </p>
<pre class="programlisting"><span class="identifier">class_</span><span class="special">&lt;</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">"Base"</span><span class="special">)</span> <pre class="programlisting">
<span class="identifier">class_</span><span class="special">&lt;</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">"Base"</span><span class="special">)</span>
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">Base</span><span class="special">::</span><span class="identifier">f</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">BaseWrap</span><span class="special">::</span><span class="identifier">default_f</span><span class="special">)</span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">Base</span><span class="special">::</span><span class="identifier">f</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">BaseWrap</span><span class="special">::</span><span class="identifier">default_f</span><span class="special">)</span>
<span class="special">;</span> <span class="special">;</span>
</pre> </pre>
<p> <p>
Take note that we expose both <code class="computeroutput"><span class="special">&amp;</span><span class="identifier">Base</span><span class="special">::</span><span class="identifier">f</span></code> and <code class="computeroutput"><span class="special">&amp;</span><span class="identifier">BaseWrap</span><span class="special">::</span><span class="identifier">default_f</span></code>. Boost.Python needs to keep track Take note that we expose both <tt class="computeroutput"><span class="special">&amp;</span><span class="identifier">Base</span><span class="special">::</span><span class="identifier">f</span></tt> and <tt class="computeroutput"><span class="special">&amp;</span><span class="identifier">BaseWrap</span><span class="special">::</span><span class="identifier">default_f</span></tt>. Boost.Python needs to keep track
of 1) the dispatch function <code class="literal">f</code> and 2) the forwarding function of 1) the dispatch function <tt class="literal">f</tt> and 2) the forwarding function
to its default implementation <code class="literal">default_f</code>. There's a special to its default implementation <tt class="literal">default_f</tt>. There's a special
<code class="literal">def</code> function for this purpose. <tt class="literal">def</tt> function for this purpose.
</p> </p>
<p> <p>
In Python, the results would be as expected: In Python, the results would be as expected:
</p> </p>
<pre class="programlisting"><span class="special">&gt;&gt;&gt;</span> <span class="identifier">base</span> <span class="special">=</span> <span class="identifier">Base</span><span class="special">()</span> <p>
</p>
<pre class="programlisting">
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">base</span> <span class="special">=</span> <span class="identifier">Base</span><span class="special">()</span>
<span class="special">&gt;&gt;&gt;</span> <span class="keyword">class</span> <span class="identifier">Derived</span><span class="special">(</span><span class="identifier">Base</span><span class="special">):</span> <span class="special">&gt;&gt;&gt;</span> <span class="keyword">class</span> <span class="identifier">Derived</span><span class="special">(</span><span class="identifier">Base</span><span class="special">):</span>
<span class="special">...</span> <span class="keyword">def</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">self</span><span class="special">):</span> <span class="special">...</span> <span class="keyword">def</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">self</span><span class="special">):</span>
<span class="special">...</span> <span class="keyword">return</span> <span class="number">42</span> <span class="special">...</span> <span class="keyword">return</span> <span class="number">42</span>
@@ -473,35 +515,40 @@
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">derived</span> <span class="special">=</span> <span class="identifier">Derived</span><span class="special">()</span> <span class="special">&gt;&gt;&gt;</span> <span class="identifier">derived</span> <span class="special">=</span> <span class="identifier">Derived</span><span class="special">()</span>
</pre> </pre>
<p> <p>
Calling <code class="literal">base.f()</code>: Calling <tt class="literal">base.f()</tt>:
</p> </p>
<pre class="programlisting"><span class="special">&gt;&gt;&gt;</span> <span class="identifier">base</span><span class="special">.</span><span class="identifier">f</span><span class="special">()</span> <pre class="programlisting">
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">base</span><span class="special">.</span><span class="identifier">f</span><span class="special">()</span>
<span class="number">0</span> <span class="number">0</span>
</pre> </pre>
<p> <p>
Calling <code class="literal">derived.f()</code>: Calling <tt class="literal">derived.f()</tt>:
</p> </p>
<pre class="programlisting"><span class="special">&gt;&gt;&gt;</span> <span class="identifier">derived</span><span class="special">.</span><span class="identifier">f</span><span class="special">()</span> <pre class="programlisting">
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">derived</span><span class="special">.</span><span class="identifier">f</span><span class="special">()</span>
<span class="number">42</span> <span class="number">42</span>
</pre> </pre>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h3 class="title"> <div class="titlepage"><div><div><h3 class="title">
<a name="python.class_operators_special_functions"></a>Class Operators/Special Functions</h3></div></div></div> <a name="python.class_operators_special_functions"></a>Class Operators/Special Functions</h3></div></div></div>
<h3> <a name="class_operators_special_functions.python_operators"></a><h2>
<a name="class_operators_special_functions.python_operators"></a> <a name="id461460"></a>
Python Operators Python Operators
</h3> </h2>
<p> <p>
C is well known for the abundance of operators. C++ extends this to the extremes C is well known for the abundance of operators. C++ extends this to the extremes
by allowing operator overloading. Boost.Python takes advantage of this and by allowing operator overloading. Boost.Python takes advantage of this and
makes it easy to wrap C++ operator-powered classes. makes it easy to wrap C++ operator-powered classes.
</p> </p>
<p> <p>
Consider a file position class <code class="literal">FilePos</code> and a set of operators Consider a file position class <tt class="literal">FilePos</tt> and a set of operators
that take on FilePos instances: that take on FilePos instances:
</p> </p>
<pre class="programlisting"><span class="keyword">class</span> <span class="identifier">FilePos</span> <span class="special">{</span> <span class="comment">/*...*/</span> <span class="special">};</span> <p>
</p>
<pre class="programlisting">
<span class="keyword">class</span> <span class="identifier">FilePos</span> <span class="special">{</span> <span class="comment">/*...*/</span> <span class="special">};</span>
<span class="identifier">FilePos</span> <span class="keyword">operator</span><span class="special">+(</span><span class="identifier">FilePos</span><span class="special">,</span> <span class="keyword">int</span><span class="special">);</span> <span class="identifier">FilePos</span> <span class="keyword">operator</span><span class="special">+(</span><span class="identifier">FilePos</span><span class="special">,</span> <span class="keyword">int</span><span class="special">);</span>
<span class="identifier">FilePos</span> <span class="keyword">operator</span><span class="special">+(</span><span class="keyword">int</span><span class="special">,</span> <span class="identifier">FilePos</span><span class="special">);</span> <span class="identifier">FilePos</span> <span class="keyword">operator</span><span class="special">+(</span><span class="keyword">int</span><span class="special">,</span> <span class="identifier">FilePos</span><span class="special">);</span>
@@ -515,28 +562,29 @@
The class and the various operators can be mapped to Python rather easily The class and the various operators can be mapped to Python rather easily
and intuitively: and intuitively:
</p> </p>
<pre class="programlisting"><span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">FilePos</span><span class="special">&gt;(</span><span class="string">"FilePos"</span><span class="special">)</span> <pre class="programlisting">
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">self</span> <span class="special">+</span> <span class="keyword">int</span><span class="special">())</span> <span class="comment">// __add__</span> <span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">FilePos</span><span class="special">&gt;(</span><span class="string">"FilePos"</span><span class="special">)</span>
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="keyword">int</span><span class="special">()</span> <span class="special">+</span> <span class="identifier">self</span><span class="special">)</span> <span class="comment">// __radd__</span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">self</span> <span class="special">+</span> <span class="keyword">int</span><span class="special">())</span> <span class="comment">// __add__
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">self</span> <span class="special">-</span> <span class="identifier">self</span><span class="special">)</span> <span class="comment">// __sub__</span> </span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="keyword">int</span><span class="special">()</span> <span class="special">+</span> <span class="identifier">self</span><span class="special">)</span> <span class="comment">// __radd__
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">self</span> <span class="special">-</span> <span class="keyword">int</span><span class="special">())</span> <span class="comment">// __sub__</span> </span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">self</span> <span class="special">-</span> <span class="identifier">self</span><span class="special">)</span> <span class="comment">// __sub__
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">self</span> <span class="special">+=</span> <span class="keyword">int</span><span class="special">())</span> <span class="comment">// __iadd__</span> </span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">self</span> <span class="special">-</span> <span class="keyword">int</span><span class="special">())</span> <span class="comment">// __sub__
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">self</span> <span class="special">-=</span> <span class="identifier">other</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;())</span> </span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">self</span> <span class="special">+=</span> <span class="keyword">int</span><span class="special">())</span> <span class="comment">// __iadd__
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">self</span> <span class="special">&lt;</span> <span class="identifier">self</span><span class="special">);</span> <span class="comment">// __lt__</span> </span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">self</span> <span class="special">-=</span> <span class="identifier">other</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;())</span>
</pre> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">self</span> <span class="special">&lt;</span> <span class="identifier">self</span><span class="special">);</span> <span class="comment">// __lt__
</span></pre>
<p> <p>
The code snippet above is very clear and needs almost no explanation at all. The code snippet above is very clear and needs almost no explanation at all.
It is virtually the same as the operators' signatures. Just take note that It is virtually the same as the operators' signatures. Just take note that
<code class="literal">self</code> refers to FilePos object. Also, not every class <tt class="literal">self</tt> refers to FilePos object. Also, not every class
<code class="literal">T</code> that you might need to interact with in an operator <tt class="literal">T</tt> that you might need to interact with in an operator
expression is (cheaply) default-constructible. You can use <code class="literal">other&lt;T&gt;()</code> expression is (cheaply) default-constructible. You can use <tt class="literal">other&lt;T&gt;()</tt>
in place of an actual <code class="literal">T</code> instance when writing "self in place of an actual <tt class="literal">T</tt> instance when writing "self
expressions". expressions".
</p> </p>
<h3> <a name="class_operators_special_functions.special_methods"></a><h2>
<a name="class_operators_special_functions.special_methods"></a> <a name="id462216"></a>
Special Methods Special Methods
</h3> </h2>
<p> <p>
Python has a few more <span class="emphasis"><em>Special Methods</em></span>. Boost.Python Python has a few more <span class="emphasis"><em>Special Methods</em></span>. Boost.Python
supports all of the standard special method names supported by real Python supports all of the standard special method names supported by real Python
@@ -544,7 +592,8 @@
wrap C++ functions that correspond to these Python <span class="emphasis"><em>special functions</em></span>. wrap C++ functions that correspond to these Python <span class="emphasis"><em>special functions</em></span>.
Example: Example:
</p> </p>
<pre class="programlisting"><span class="keyword">class</span> <span class="identifier">Rational</span> <pre class="programlisting">
<span class="keyword">class</span> <span class="identifier">Rational</span>
<span class="special">{</span> <span class="keyword">public</span><span class="special">:</span> <span class="keyword">operator</span> <span class="keyword">double</span><span class="special">()</span> <span class="keyword">const</span><span class="special">;</span> <span class="special">};</span> <span class="special">{</span> <span class="keyword">public</span><span class="special">:</span> <span class="keyword">operator</span> <span class="keyword">double</span><span class="special">()</span> <span class="keyword">const</span><span class="special">;</span> <span class="special">};</span>
<span class="identifier">Rational</span> <span class="identifier">pow</span><span class="special">(</span><span class="identifier">Rational</span><span class="special">,</span> <span class="identifier">Rational</span><span class="special">);</span> <span class="identifier">Rational</span> <span class="identifier">pow</span><span class="special">(</span><span class="identifier">Rational</span><span class="special">,</span> <span class="identifier">Rational</span><span class="special">);</span>
@@ -552,30 +601,30 @@
<span class="identifier">ostream</span><span class="special">&amp;</span> <span class="keyword">operator</span><span class="special">&lt;&lt;(</span><span class="identifier">ostream</span><span class="special">&amp;,</span><span class="identifier">Rational</span><span class="special">);</span> <span class="identifier">ostream</span><span class="special">&amp;</span> <span class="keyword">operator</span><span class="special">&lt;&lt;(</span><span class="identifier">ostream</span><span class="special">&amp;,</span><span class="identifier">Rational</span><span class="special">);</span>
<span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">Rational</span><span class="special">&gt;(</span><span class="string">"Rational"</span><span class="special">)</span> <span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">Rational</span><span class="special">&gt;(</span><span class="string">"Rational"</span><span class="special">)</span>
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">float_</span><span class="special">(</span><span class="identifier">self</span><span class="special">))</span> <span class="comment">// __float__</span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">float_</span><span class="special">(</span><span class="identifier">self</span><span class="special">))</span> <span class="comment">// __float__
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">pow</span><span class="special">(</span><span class="identifier">self</span><span class="special">,</span> <span class="identifier">other</span><span class="special">&lt;</span><span class="identifier">Rational</span><span class="special">&gt;))</span> <span class="comment">// __pow__</span> </span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">pow</span><span class="special">(</span><span class="identifier">self</span><span class="special">,</span> <span class="identifier">other</span><span class="special">&lt;</span><span class="identifier">Rational</span><span class="special">&gt;))</span> <span class="comment">// __pow__
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">abs</span><span class="special">(</span><span class="identifier">self</span><span class="special">))</span> <span class="comment">// __abs__</span> </span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">abs</span><span class="special">(</span><span class="identifier">self</span><span class="special">))</span> <span class="comment">// __abs__
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">str</span><span class="special">(</span><span class="identifier">self</span><span class="special">))</span> <span class="comment">// __str__</span> </span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">str</span><span class="special">(</span><span class="identifier">self</span><span class="special">))</span> <span class="comment">// __str__
<span class="special">;</span> </span> <span class="special">;</span>
</pre> </pre>
<p> <p>
Need we say more? Need we say more?
</p> </p>
<div class="note"><table border="0" summary="Note"> <div class="note"><table border="0" summary="Note">
<tr> <tr>
<td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../../../doc/src/images/note.png"></td> <td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../../../doc/html/images/note.png"></td>
<th align="left">Note</th> <th align="left">Note</th>
</tr> </tr>
<tr><td align="left" valign="top"><p> <tr><td colspan="2" align="left" valign="top"><p>
What is the business of <code class="computeroutput"><span class="keyword">operator</span><span class="special">&lt;&lt;</span></code>? Well, the method <code class="computeroutput"><span class="identifier">str</span></code> requires the <code class="computeroutput"><span class="keyword">operator</span><span class="special">&lt;&lt;</span></code> to do its work (i.e. <code class="computeroutput"><span class="keyword">operator</span><span class="special">&lt;&lt;</span></code> What is the business of <tt class="computeroutput"><span class="keyword">operator</span><span class="special">&lt;&lt;</span></tt>? Well, the method <tt class="computeroutput"><span class="identifier">str</span></tt> requires the <tt class="computeroutput"><span class="keyword">operator</span><span class="special">&lt;&lt;</span></tt> to do its work (i.e. <tt class="computeroutput"><span class="keyword">operator</span><span class="special">&lt;&lt;</span></tt>
is used by the method defined by <code class="computeroutput"><span class="identifier">def</span><span class="special">(</span><span class="identifier">str</span><span class="special">(</span><span class="identifier">self</span><span class="special">))</span></code>. is used by the method defined by <tt class="computeroutput"><span class="identifier">def</span><span class="special">(</span><span class="identifier">str</span><span class="special">(</span><span class="identifier">self</span><span class="special">))</span></tt>.
</p></td></tr> </p></td></tr>
</table></div> </table></div>
</div> </div>
</div> </div>
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr> <table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
<td align="left"></td> <td align="left"></td>
<td align="right"><div class="copyright-footer">Copyright &#169; 2002-2005 Joel <td align="right"><div class="copyright-footer">Copyright © 2002-2005 Joel
de Guzman, David Abrahams<p> de Guzman, David Abrahams<p>
Distributed under the Boost Software License, Version 1.0. (See accompanying Distributed under the Boost Software License, Version 1.0. (See accompanying
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top"> file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">
@@ -585,7 +634,7 @@
</tr></table> </tr></table>
<hr> <hr>
<div class="spirit-nav"> <div class="spirit-nav">
<a accesskey="p" href="hello.html"><img src="../../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="functions.html"><img src="../../../../../../../doc/src/images/next.png" alt="Next"></a> <a accesskey="p" href="hello.html"><img src="../../../../../../../doc/html/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/html/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/html/images/home.png" alt="Home"></a><a accesskey="n" href="functions.html"><img src="../../../../../../../doc/html/images/next.png" alt="Next"></a>
</div> </div>
</body> </body>
</html> </html>

View File

@@ -1,28 +1,28 @@
<html> <html>
<head> <head>
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII"> <meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
<title>Functions</title> <title>Functions</title>
<link rel="stylesheet" href="../../../../../../../doc/src/boostbook.css" type="text/css"> <link rel="stylesheet" href="../../../../../../../doc/html/boostbook.css" type="text/css">
<meta name="generator" content="DocBook XSL Stylesheets V1.76.1"> <meta name="generator" content="DocBook XSL Stylesheets V1.66.1">
<link rel="home" href="../index.html" title="Chapter&#160;1.&#160;python 2.0"> <link rel="start" href="../index.html" title="Chapter 1. python 1.0">
<link rel="up" href="../index.html" title="Chapter&#160;1.&#160;python 2.0"> <link rel="up" href="../index.html" title="Chapter 1. python 1.0">
<link rel="prev" href="exposing.html" title="Exposing Classes"> <link rel="prev" href="exposing.html" title=" Exposing Classes">
<link rel="next" href="object.html" title="Object Interface"> <link rel="next" href="object.html" title=" Object Interface">
</head> </head>
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"> <body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
<table cellpadding="2" width="100%"><tr> <table cellpadding="2" width="100%"><tr>
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../../boost.png"></td> <td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../../boost.png"></td>
<td align="center"><a href="../../../../../../../index.html">Home</a></td> <td align="center"><a href="../../../../../../../index.htm">Home</a></td>
<td align="center"><a href="../../../../../../../libs/libraries.htm">Libraries</a></td> <td align="center"><a href="../../../../../../../libs/libraries.htm">Libraries</a></td>
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td> <td align="center"><a href="../../../../../../../people/people.htm">People</a></td>
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td> <td align="center"><a href="../../../../../../../more/faq.htm">FAQ</a></td>
<td align="center"><a href="../../../../../../../more/index.htm">More</a></td> <td align="center"><a href="../../../../../../../more/index.htm">More</a></td>
</tr></table> </tr></table>
<hr> <hr>
<div class="spirit-nav"> <div class="spirit-nav">
<a accesskey="p" href="exposing.html"><img src="../../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="object.html"><img src="../../../../../../../doc/src/images/next.png" alt="Next"></a> <a accesskey="p" href="exposing.html"><img src="../../../../../../../doc/html/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/html/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/html/images/home.png" alt="Home"></a><a accesskey="n" href="object.html"><img src="../../../../../../../doc/html/images/next.png" alt="Next"></a>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h2 class="title" style="clear: both"> <div class="titlepage"><div><div><h2 class="title" style="clear: both">
<a name="python.functions"></a>Functions</h2></div></div></div> <a name="python.functions"></a>Functions</h2></div></div></div>
<div class="toc"><dl> <div class="toc"><dl>
@@ -38,12 +38,18 @@
facilities that will make it even easier for us to expose C++ functions that facilities that will make it even easier for us to expose C++ functions that
take advantage of C++ features such as overloading and default arguments. take advantage of C++ features such as overloading and default arguments.
</p> </p>
<div class="blockquote"><blockquote class="blockquote"><p> <div class="blockquote"><blockquote class="blockquote">
<span class="emphasis"><em>Read on...</em></span> <p>
</p></blockquote></div> </p>
<p>
<span class="emphasis"><em>Read on...</em></span>
</p>
<p>
</p>
</blockquote></div>
<p> <p>
But before you do, you might want to fire up Python 2.2 or later and type But before you do, you might want to fire up Python 2.2 or later and type
<code class="literal">&gt;&gt;&gt; import this</code>. <tt class="literal">&gt;&gt;&gt; import this</tt>.
</p> </p>
<pre class="programlisting">&gt;&gt;&gt; import this <pre class="programlisting">&gt;&gt;&gt; import this
The Zen of Python, by Tim Peters The Zen of Python, by Tim Peters
@@ -62,12 +68,12 @@ In the face of ambiguity, refuse the temptation to guess.
There should be one-- and preferably only one --obvious way to do it There should be one-- and preferably only one --obvious way to do it
Although that way may not be obvious at first unless you're Dutch. Although that way may not be obvious at first unless you're Dutch.
Now is better than never. Now is better than never.
Although never is often better than <span class="bold"><strong>right</strong></span> now. Although never is often better than <span class="bold"><b>right</b></span> now.
If the implementation is hard to explain, it's a bad idea. If the implementation is hard to explain, it's a bad idea.
If the implementation is easy to explain, it may be a good idea. If the implementation is easy to explain, it may be a good idea.
Namespaces are one honking great idea -- let's do more of those! Namespaces are one honking great idea -- let's do more of those!
</pre> </pre>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h3 class="title"> <div class="titlepage"><div><div><h3 class="title">
<a name="python.call_policies"></a>Call Policies</h3></div></div></div> <a name="python.call_policies"></a>Call Policies</h3></div></div></div>
<p> <p>
@@ -81,14 +87,16 @@ Namespaces are one honking great idea -- let's do more of those!
so Boost.Python must deal with them. To do this, it may need your help. Consider so Boost.Python must deal with them. To do this, it may need your help. Consider
the following C++ function: the following C++ function:
</p> </p>
<pre class="programlisting"><span class="identifier">X</span><span class="special">&amp;</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">Y</span><span class="special">&amp;</span> <span class="identifier">y</span><span class="special">,</span> <span class="identifier">Z</span><span class="special">*</span> <span class="identifier">z</span><span class="special">);</span> <pre class="programlisting">
<span class="identifier">X</span><span class="special">&amp;</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">Y</span><span class="special">&amp;</span> <span class="identifier">y</span><span class="special">,</span> <span class="identifier">Z</span><span class="special">*</span> <span class="identifier">z</span><span class="special">);</span>
</pre> </pre>
<p> <p>
How should the library wrap this function? A naive approach builds a Python How should the library wrap this function? A naive approach builds a Python
X object around result reference. This strategy might or might not work out. X object around result reference. This strategy might or might not work out.
Here's an example where it didn't Here's an example where it didn't
</p> </p>
<pre class="programlisting"><span class="special">&gt;&gt;&gt;</span> <span class="identifier">x</span> <span class="special">=</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">y</span><span class="special">,</span> <span class="identifier">z</span><span class="special">)</span> <span class="preprocessor"># x</span> <span class="identifier">refers</span> <span class="identifier">to</span> <span class="identifier">some</span> <span class="identifier">C</span><span class="special">++</span> <span class="identifier">X</span> <pre class="programlisting">
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">x</span> <span class="special">=</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">y</span><span class="special">,</span> <span class="identifier">z</span><span class="special">)</span> <span class="preprocessor"># x</span> <span class="identifier">refers</span> <span class="identifier">to</span> <span class="identifier">some</span> <span class="identifier">C</span><span class="special">++</span> <span class="identifier">X</span>
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">del</span> <span class="identifier">y</span> <span class="special">&gt;&gt;&gt;</span> <span class="identifier">del</span> <span class="identifier">y</span>
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">some_method</span><span class="special">()</span> <span class="preprocessor"># CRASH</span><span class="special">!</span> <span class="special">&gt;&gt;&gt;</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">some_method</span><span class="special">()</span> <span class="preprocessor"># CRASH</span><span class="special">!</span>
</pre> </pre>
@@ -98,7 +106,8 @@ Namespaces are one honking great idea -- let's do more of those!
<p> <p>
Well, what if f() was implemented as shown below: Well, what if f() was implemented as shown below:
</p> </p>
<pre class="programlisting"><span class="identifier">X</span><span class="special">&amp;</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">Y</span><span class="special">&amp;</span> <span class="identifier">y</span><span class="special">,</span> <span class="identifier">Z</span><span class="special">*</span> <span class="identifier">z</span><span class="special">)</span> <pre class="programlisting">
<span class="identifier">X</span><span class="special">&amp;</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">Y</span><span class="special">&amp;</span> <span class="identifier">y</span><span class="special">,</span> <span class="identifier">Z</span><span class="special">*</span> <span class="identifier">z</span><span class="special">)</span>
<span class="special">{</span> <span class="special">{</span>
<span class="identifier">y</span><span class="special">.</span><span class="identifier">z</span> <span class="special">=</span> <span class="identifier">z</span><span class="special">;</span> <span class="identifier">y</span><span class="special">.</span><span class="identifier">z</span> <span class="special">=</span> <span class="identifier">z</span><span class="special">;</span>
<span class="keyword">return</span> <span class="identifier">y</span><span class="special">.</span><span class="identifier">x</span><span class="special">;</span> <span class="keyword">return</span> <span class="identifier">y</span><span class="special">.</span><span class="identifier">x</span><span class="special">;</span>
@@ -115,30 +124,31 @@ Namespaces are one honking great idea -- let's do more of those!
<p> <p>
Here's what's happening: Here's what's happening:
</p> </p>
<div class="orderedlist"><ol class="orderedlist" type="1"> <div class="orderedlist"><ol type="1">
<li class="listitem"> <li>
<code class="literal">f</code> is called passing in a reference to <code class="literal">y</code> <tt class="literal">f</tt> is called passing in a reference to <tt class="literal">y</tt>
and a pointer to <code class="literal">z</code> and a pointer to <tt class="literal">z</tt>
</li> </li>
<li class="listitem"> <li>
A reference to <code class="literal">y.x</code> is returned A reference to <tt class="literal">y.x</tt> is returned
</li> </li>
<li class="listitem"> <li>
<code class="literal">y</code> is deleted. <code class="literal">x</code> is a dangling reference <tt class="literal">y</tt> is deleted. <tt class="literal">x</tt> is a dangling reference
</li> </li>
<li class="listitem"> <li>
<code class="literal">x.some_method()</code> is called <tt class="literal">x.some_method()</tt> is called
</li> </li>
<li class="listitem"> <li><span class="bold"><b>BOOM!</b></span></li>
<span class="bold"><strong>BOOM!</strong></span>
</li>
</ol></div> </ol></div>
<p> <p>
We could copy result into a new object: We could copy result into a new object:
</p> </p>
<pre class="programlisting"><span class="special">&gt;&gt;&gt;</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">y</span><span class="special">,</span> <span class="identifier">z</span><span class="special">).</span><span class="identifier">set</span><span class="special">(</span><span class="number">42</span><span class="special">)</span> <span class="comment"># Result disappears</span> <p>
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">y</span><span class="special">.</span><span class="identifier">x</span><span class="special">.</span><span class="identifier">get</span><span class="special">()</span> <span class="comment"># No crash, but still bad</span> </p>
<span class="number">3.14</span> <pre class="programlisting">
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">y</span><span class="special">,</span> <span class="identifier">z</span><span class="special">).</span><span class="identifier">set</span><span class="special">(</span><span class="number">42</span><span class="special">)</span> <span class="comment"># Result disappears
</span><span class="special">&gt;&gt;&gt;</span> <span class="identifier">y</span><span class="special">.</span><span class="identifier">x</span><span class="special">.</span><span class="identifier">get</span><span class="special">()</span> <span class="comment"># No crash, but still bad
</span><span class="number">3.14</span>
</pre> </pre>
<p> <p>
This is not really our intent of our C++ interface. We've broken our promise This is not really our intent of our C++ interface. We've broken our promise
@@ -148,24 +158,29 @@ Namespaces are one honking great idea -- let's do more of those!
<p> <p>
Our problems do not end there. Suppose Y is implemented as follows: Our problems do not end there. Suppose Y is implemented as follows:
</p> </p>
<pre class="programlisting"><span class="keyword">struct</span> <span class="identifier">Y</span> <p>
</p>
<pre class="programlisting">
<span class="keyword">struct</span> <span class="identifier">Y</span>
<span class="special">{</span> <span class="special">{</span>
<span class="identifier">X</span> <span class="identifier">x</span><span class="special">;</span> <span class="identifier">Z</span><span class="special">*</span> <span class="identifier">z</span><span class="special">;</span> <span class="identifier">X</span> <span class="identifier">x</span><span class="special">;</span> <span class="identifier">Z</span><span class="special">*</span> <span class="identifier">z</span><span class="special">;</span>
<span class="keyword">int</span> <span class="identifier">z_value</span><span class="special">()</span> <span class="special">{</span> <span class="keyword">return</span> <span class="identifier">z</span><span class="special">-&gt;</span><span class="identifier">value</span><span class="special">();</span> <span class="special">}</span> <span class="keyword">int</span> <span class="identifier">z_value</span><span class="special">()</span> <span class="special">{</span> <span class="keyword">return</span> <span class="identifier">z</span><span class="special">-&gt;</span><span class="identifier">value</span><span class="special">();</span> <span class="special">}</span>
<span class="special">};</span> <span class="special">};</span>
</pre> </pre>
<p> <p>
Notice that the data member <code class="literal">z</code> is held by class Y using Notice that the data member <tt class="literal">z</tt> is held by class Y using
a raw pointer. Now we have a potential dangling pointer problem inside Y: a raw pointer. Now we have a potential dangling pointer problem inside Y:
</p> </p>
<pre class="programlisting"><span class="special">&gt;&gt;&gt;</span> <span class="identifier">x</span> <span class="special">=</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">y</span><span class="special">,</span> <span class="identifier">z</span><span class="special">)</span> <span class="preprocessor"># y</span> <span class="identifier">refers</span> <span class="identifier">to</span> <span class="identifier">z</span> <pre class="programlisting">
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">x</span> <span class="special">=</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">y</span><span class="special">,</span> <span class="identifier">z</span><span class="special">)</span> <span class="preprocessor"># y</span> <span class="identifier">refers</span> <span class="identifier">to</span> <span class="identifier">z</span>
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">del</span> <span class="identifier">z</span> <span class="preprocessor"># Kill</span> <span class="identifier">the</span> <span class="identifier">z</span> <span class="identifier">object</span> <span class="special">&gt;&gt;&gt;</span> <span class="identifier">del</span> <span class="identifier">z</span> <span class="preprocessor"># Kill</span> <span class="identifier">the</span> <span class="identifier">z</span> <span class="identifier">object</span>
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">y</span><span class="special">.</span><span class="identifier">z_value</span><span class="special">()</span> <span class="preprocessor"># CRASH</span><span class="special">!</span> <span class="special">&gt;&gt;&gt;</span> <span class="identifier">y</span><span class="special">.</span><span class="identifier">z_value</span><span class="special">()</span> <span class="preprocessor"># CRASH</span><span class="special">!</span>
</pre> </pre>
<p> <p>
For reference, here's the implementation of <code class="literal">f</code> again: For reference, here's the implementation of <tt class="literal">f</tt> again:
</p> </p>
<pre class="programlisting"><span class="identifier">X</span><span class="special">&amp;</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">Y</span><span class="special">&amp;</span> <span class="identifier">y</span><span class="special">,</span> <span class="identifier">Z</span><span class="special">*</span> <span class="identifier">z</span><span class="special">)</span> <pre class="programlisting">
<span class="identifier">X</span><span class="special">&amp;</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">Y</span><span class="special">&amp;</span> <span class="identifier">y</span><span class="special">,</span> <span class="identifier">Z</span><span class="special">*</span> <span class="identifier">z</span><span class="special">)</span>
<span class="special">{</span> <span class="special">{</span>
<span class="identifier">y</span><span class="special">.</span><span class="identifier">z</span> <span class="special">=</span> <span class="identifier">z</span><span class="special">;</span> <span class="identifier">y</span><span class="special">.</span><span class="identifier">z</span> <span class="special">=</span> <span class="identifier">z</span><span class="special">;</span>
<span class="keyword">return</span> <span class="identifier">y</span><span class="special">.</span><span class="identifier">x</span><span class="special">;</span> <span class="keyword">return</span> <span class="identifier">y</span><span class="special">.</span><span class="identifier">x</span><span class="special">;</span>
@@ -174,70 +189,71 @@ Namespaces are one honking great idea -- let's do more of those!
<p> <p>
Here's what's happening: Here's what's happening:
</p> </p>
<div class="orderedlist"><ol class="orderedlist" type="1"> <div class="orderedlist"><ol type="1">
<li class="listitem"> <li>
<code class="literal">f</code> is called passing in a reference to <code class="literal">y</code> <tt class="literal">f</tt> is called passing in a reference to <tt class="literal">y</tt>
and a pointer to <code class="literal">z</code> and a pointer to <tt class="literal">z</tt>
</li> </li>
<li class="listitem"> <li>
A pointer to <code class="literal">z</code> is held by <code class="literal">y</code> A pointer to <tt class="literal">z</tt> is held by <tt class="literal">y</tt>
</li> </li>
<li class="listitem"> <li>
A reference to <code class="literal">y.x</code> is returned A reference to <tt class="literal">y.x</tt> is returned
</li> </li>
<li class="listitem"> <li>
<code class="literal">z</code> is deleted. <code class="literal">y.z</code> is a dangling <tt class="literal">z</tt> is deleted. <tt class="literal">y.z</tt> is a dangling pointer
pointer </li>
</li> <li>
<li class="listitem"> <tt class="literal">y.z_value()</tt> is called
<code class="literal">y.z_value()</code> is called </li>
</li> <li>
<li class="listitem"> <tt class="literal">z-&gt;value()</tt> is called
<code class="literal">z-&gt;value()</code> is called </li>
</li> <li><span class="bold"><b>BOOM!</b></span></li>
<li class="listitem">
<span class="bold"><strong>BOOM!</strong></span>
</li>
</ol></div> </ol></div>
<h3> <a name="call_policies.call_policies"></a><h2>
<a name="call_policies.call_policies"></a> <a name="id464076"></a>
Call Policies Call Policies
</h3> </h2>
<p> <p>
Call Policies may be used in situations such as the example detailed above. Call Policies may be used in situations such as the example detailed above.
In our example, <code class="literal">return_internal_reference</code> and <code class="literal">with_custodian_and_ward</code> In our example, <tt class="literal">return_internal_reference</tt> and <tt class="literal">with_custodian_and_ward</tt>
are our friends: are our friends:
</p> </p>
<pre class="programlisting"><span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">f</span><span class="special">,</span> <pre class="programlisting">
<span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">f</span><span class="special">,</span>
<span class="identifier">return_internal_reference</span><span class="special">&lt;</span><span class="number">1</span><span class="special">,</span> <span class="identifier">return_internal_reference</span><span class="special">&lt;</span><span class="number">1</span><span class="special">,</span>
<span class="identifier">with_custodian_and_ward</span><span class="special">&lt;</span><span class="number">1</span><span class="special">,</span> <span class="number">2</span><span class="special">&gt;</span> <span class="special">&gt;());</span> <span class="identifier">with_custodian_and_ward</span><span class="special">&lt;</span><span class="number">1</span><span class="special">,</span> <span class="number">2</span><span class="special">&gt;</span> <span class="special">&gt;());</span>
</pre> </pre>
<p> <p>
What are the <code class="literal">1</code> and <code class="literal">2</code> parameters, you What are the <tt class="literal">1</tt> and <tt class="literal">2</tt> parameters, you
ask? ask?
</p> </p>
<pre class="programlisting"><span class="identifier">return_internal_reference</span><span class="special">&lt;</span><span class="number">1</span> <pre class="programlisting">
<span class="identifier">return_internal_reference</span><span class="special">&lt;</span><span class="number">1</span>
</pre> </pre>
<p> <p>
Informs Boost.Python that the first argument, in our case <code class="literal">Y&amp; Informs Boost.Python that the first argument, in our case <tt class="literal">Y&amp;
y</code>, is the owner of the returned reference: <code class="literal">X&amp;</code>. y</tt>, is the owner of the returned reference: <tt class="literal">X&amp;</tt>.
The "<code class="literal">1</code>" simply specifies the first argument. The "<tt class="literal">1</tt>" simply specifies the first argument.
In short: "return an internal reference <code class="literal">X&amp;</code> owned In short: "return an internal reference <tt class="literal">X&amp;</tt> owned
by the 1st argument <code class="literal">Y&amp; y</code>". by the 1st argument <tt class="literal">Y&amp; y</tt>".
</p> </p>
<pre class="programlisting"><span class="identifier">with_custodian_and_ward</span><span class="special">&lt;</span><span class="number">1</span><span class="special">,</span> <span class="number">2</span><span class="special">&gt;</span> <pre class="programlisting">
<span class="identifier">with_custodian_and_ward</span><span class="special">&lt;</span><span class="number">1</span><span class="special">,</span> <span class="number">2</span><span class="special">&gt;</span>
</pre> </pre>
<p> <p>
Informs Boost.Python that the lifetime of the argument indicated by ward Informs Boost.Python that the lifetime of the argument indicated by ward
(i.e. the 2nd argument: <code class="literal">Z* z</code>) is dependent on the lifetime (i.e. the 2nd argument: <tt class="literal">Z* z</tt>) is dependent on the lifetime
of the argument indicated by custodian (i.e. the 1st argument: <code class="literal">Y&amp; of the argument indicated by custodian (i.e. the 1st argument: <tt class="literal">Y&amp;
y</code>). y</tt>).
</p> </p>
<p> <p>
It is also important to note that we have defined two policies above. Two It is also important to note that we have defined two policies above. Two
or more policies can be composed by chaining. Here's the general syntax: or more policies can be composed by chaining. Here's the general syntax:
</p> </p>
<pre class="programlisting"><span class="identifier">policy1</span><span class="special">&lt;</span><span class="identifier">args</span><span class="special">...,</span> <pre class="programlisting">
<span class="identifier">policy1</span><span class="special">&lt;</span><span class="identifier">args</span><span class="special">...,</span>
<span class="identifier">policy2</span><span class="special">&lt;</span><span class="identifier">args</span><span class="special">...,</span> <span class="identifier">policy2</span><span class="special">&lt;</span><span class="identifier">args</span><span class="special">...,</span>
<span class="identifier">policy3</span><span class="special">&lt;</span><span class="identifier">args</span><span class="special">...&gt;</span> <span class="special">&gt;</span> <span class="special">&gt;</span> <span class="identifier">policy3</span><span class="special">&lt;</span><span class="identifier">args</span><span class="special">...&gt;</span> <span class="special">&gt;</span> <span class="special">&gt;</span>
</pre> </pre>
@@ -245,44 +261,42 @@ Namespaces are one honking great idea -- let's do more of those!
Here is the list of predefined call policies. A complete reference detailing Here is the list of predefined call policies. A complete reference detailing
these can be found <a href="../../../../v2/reference.html#models_of_call_policies" target="_top">here</a>. these can be found <a href="../../../../v2/reference.html#models_of_call_policies" target="_top">here</a>.
</p> </p>
<div class="itemizedlist"><ul class="itemizedlist" type="disc"> <div class="itemizedlist"><ul type="disc">
<li class="listitem"> <li>
<span class="bold"><strong>with_custodian_and_ward</strong></span>: Ties lifetimes <span class="bold"><b>with_custodian_and_ward</b></span>: Ties lifetimes
of the arguments of the arguments
</li> </li>
<li class="listitem"> <li>
<span class="bold"><strong>with_custodian_and_ward_postcall</strong></span>: Ties <span class="bold"><b>with_custodian_and_ward_postcall</b></span>: Ties
lifetimes of the arguments and results lifetimes of the arguments and results
</li> </li>
<li class="listitem"> <li>
<span class="bold"><strong>return_internal_reference</strong></span>: Ties lifetime <span class="bold"><b>return_internal_reference</b></span>: Ties lifetime
of one argument to that of result of one argument to that of result
</li> </li>
<li class="listitem"> <li>
<span class="bold"><strong>return_value_policy&lt;T&gt; with T one of:</strong></span> <span class="bold"><b>return_value_policy&lt;T&gt; with T one of:</b></span><div class="itemizedlist"><ul type="circle">
<div class="itemizedlist"><ul class="itemizedlist" type="circle"> <li>
<li class="listitem"> <span class="bold"><b>reference_existing_object</b></span>: naive (dangerous)
<span class="bold"><strong>reference_existing_object</strong></span>: naive approach
(dangerous) approach </li>
</li> <li>
<li class="listitem"> <span class="bold"><b>copy_const_reference</b></span>: Boost.Python
<span class="bold"><strong>copy_const_reference</strong></span>: Boost.Python v1 approach
v1 approach </li>
</li> <li>
<li class="listitem"> <span class="bold"><b>copy_non_const_reference</b></span>:
<span class="bold"><strong>copy_non_const_reference</strong></span>: </li>
</li> <li>
<li class="listitem"> <span class="bold"><b>manage_new_object</b></span>: Adopt a pointer
<span class="bold"><strong>manage_new_object</strong></span>: Adopt a pointer and hold the instance
and hold the instance </li>
</li>
</ul></div> </ul></div>
</li> </li>
</ul></div> </ul></div>
<div class="sidebar"> <div class="sidebar">
<div class="titlepage"></div>
<p> <p>
<span class="inlinemediaobject"><img src="../images/smiley.png" alt="smiley"></span> <span class="bold"><strong>Remember the Zen, Luke:</strong></span> <span class="inlinemediaobject"><img src="../images/smiley.png" alt="smiley"></span> <span class="bold"><b>Remember the Zen, Luke:</b></span>
</p> </p>
<p> <p>
"Explicit is better than implicit" "Explicit is better than implicit"
@@ -292,7 +306,7 @@ Namespaces are one honking great idea -- let's do more of those!
</p> </p>
</div> </div>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h3 class="title"> <div class="titlepage"><div><div><h3 class="title">
<a name="python.overloading"></a>Overloading</h3></div></div></div> <a name="python.overloading"></a>Overloading</h3></div></div></div>
<p> <p>
@@ -303,7 +317,8 @@ Namespaces are one honking great idea -- let's do more of those!
<p> <p>
We have here our C++ class: We have here our C++ class:
</p> </p>
<pre class="programlisting"><span class="keyword">struct</span> <span class="identifier">X</span> <pre class="programlisting">
<span class="keyword">struct</span> <span class="identifier">X</span>
<span class="special">{</span> <span class="special">{</span>
<span class="keyword">bool</span> <span class="identifier">f</span><span class="special">(</span><span class="keyword">int</span> <span class="identifier">a</span><span class="special">)</span> <span class="keyword">bool</span> <span class="identifier">f</span><span class="special">(</span><span class="keyword">int</span> <span class="identifier">a</span><span class="special">)</span>
<span class="special">{</span> <span class="special">{</span>
@@ -330,7 +345,8 @@ Namespaces are one honking great idea -- let's do more of those!
Class X has 4 overloaded functions. We will start by introducing some member Class X has 4 overloaded functions. We will start by introducing some member
function pointer variables: function pointer variables:
</p> </p>
<pre class="programlisting"><span class="keyword">bool</span> <span class="special">(</span><span class="identifier">X</span><span class="special">::*</span><span class="identifier">fx1</span><span class="special">)(</span><span class="keyword">int</span><span class="special">)</span> <span class="special">=</span> <span class="special">&amp;</span><span class="identifier">X</span><span class="special">::</span><span class="identifier">f</span><span class="special">;</span> <pre class="programlisting">
<span class="keyword">bool</span> <span class="special">(</span><span class="identifier">X</span><span class="special">::*</span><span class="identifier">fx1</span><span class="special">)(</span><span class="keyword">int</span><span class="special">)</span> <span class="special">=</span> <span class="special">&amp;</span><span class="identifier">X</span><span class="special">::</span><span class="identifier">f</span><span class="special">;</span>
<span class="keyword">bool</span> <span class="special">(</span><span class="identifier">X</span><span class="special">::*</span><span class="identifier">fx2</span><span class="special">)(</span><span class="keyword">int</span><span class="special">,</span> <span class="keyword">double</span><span class="special">)</span> <span class="special">=</span> <span class="special">&amp;</span><span class="identifier">X</span><span class="special">::</span><span class="identifier">f</span><span class="special">;</span> <span class="keyword">bool</span> <span class="special">(</span><span class="identifier">X</span><span class="special">::*</span><span class="identifier">fx2</span><span class="special">)(</span><span class="keyword">int</span><span class="special">,</span> <span class="keyword">double</span><span class="special">)</span> <span class="special">=</span> <span class="special">&amp;</span><span class="identifier">X</span><span class="special">::</span><span class="identifier">f</span><span class="special">;</span>
<span class="keyword">bool</span> <span class="special">(</span><span class="identifier">X</span><span class="special">::*</span><span class="identifier">fx3</span><span class="special">)(</span><span class="keyword">int</span><span class="special">,</span> <span class="keyword">double</span><span class="special">,</span> <span class="keyword">char</span><span class="special">)=</span> <span class="special">&amp;</span><span class="identifier">X</span><span class="special">::</span><span class="identifier">f</span><span class="special">;</span> <span class="keyword">bool</span> <span class="special">(</span><span class="identifier">X</span><span class="special">::*</span><span class="identifier">fx3</span><span class="special">)(</span><span class="keyword">int</span><span class="special">,</span> <span class="keyword">double</span><span class="special">,</span> <span class="keyword">char</span><span class="special">)=</span> <span class="special">&amp;</span><span class="identifier">X</span><span class="special">::</span><span class="identifier">f</span><span class="special">;</span>
<span class="keyword">int</span> <span class="special">(</span><span class="identifier">X</span><span class="special">::*</span><span class="identifier">fx4</span><span class="special">)(</span><span class="keyword">int</span><span class="special">,</span> <span class="keyword">int</span><span class="special">,</span> <span class="keyword">int</span><span class="special">)</span> <span class="special">=</span> <span class="special">&amp;</span><span class="identifier">X</span><span class="special">::</span><span class="identifier">f</span><span class="special">;</span> <span class="keyword">int</span> <span class="special">(</span><span class="identifier">X</span><span class="special">::*</span><span class="identifier">fx4</span><span class="special">)(</span><span class="keyword">int</span><span class="special">,</span> <span class="keyword">int</span><span class="special">,</span> <span class="keyword">int</span><span class="special">)</span> <span class="special">=</span> <span class="special">&amp;</span><span class="identifier">X</span><span class="special">::</span><span class="identifier">f</span><span class="special">;</span>
@@ -338,69 +354,75 @@ Namespaces are one honking great idea -- let's do more of those!
<p> <p>
With these in hand, we can proceed to define and wrap this for Python: With these in hand, we can proceed to define and wrap this for Python:
</p> </p>
<pre class="programlisting"><span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">fx1</span><span class="special">)</span> <pre class="programlisting">
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">fx1</span><span class="special">)</span>
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">fx2</span><span class="special">)</span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">fx2</span><span class="special">)</span>
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">fx3</span><span class="special">)</span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">fx3</span><span class="special">)</span>
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">fx4</span><span class="special">)</span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">fx4</span><span class="special">)</span>
</pre> </pre>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h3 class="title"> <div class="titlepage"><div><div><h3 class="title">
<a name="python.default_arguments"></a>Default Arguments</h3></div></div></div> <a name="python.default_arguments"></a>Default Arguments</h3></div></div></div>
<p> <p>
Boost.Python wraps (member) function pointers. Unfortunately, C++ function Boost.Python wraps (member) function pointers. Unfortunately, C++ function
pointers carry no default argument info. Take a function <code class="literal">f</code> pointers carry no default argument info. Take a function <tt class="literal">f</tt>
with default arguments: with default arguments:
</p> </p>
<pre class="programlisting"><span class="keyword">int</span> <span class="identifier">f</span><span class="special">(</span><span class="keyword">int</span><span class="special">,</span> <span class="keyword">double</span> <span class="special">=</span> <span class="number">3.14</span><span class="special">,</span> <span class="keyword">char</span> <span class="keyword">const</span><span class="special">*</span> <span class="special">=</span> <span class="string">"hello"</span><span class="special">);</span> <pre class="programlisting">
<span class="keyword">int</span> <span class="identifier">f</span><span class="special">(</span><span class="keyword">int</span><span class="special">,</span> <span class="keyword">double</span> <span class="special">=</span> <span class="number">3.14</span><span class="special">,</span> <span class="keyword">char</span> <span class="keyword">const</span><span class="special">*</span> <span class="special">=</span> <span class="string">"hello"</span><span class="special">);</span>
</pre> </pre>
<p> <p>
But the type of a pointer to the function <code class="literal">f</code> has no information But the type of a pointer to the function <tt class="literal">f</tt> has no information
about its default arguments: about its default arguments:
</p> </p>
<pre class="programlisting"><span class="keyword">int</span><span class="special">(*</span><span class="identifier">g</span><span class="special">)(</span><span class="keyword">int</span><span class="special">,</span><span class="keyword">double</span><span class="special">,</span><span class="keyword">char</span> <span class="keyword">const</span><span class="special">*)</span> <span class="special">=</span> <span class="identifier">f</span><span class="special">;</span> <span class="comment">// defaults lost!</span> <pre class="programlisting">
</pre> <span class="keyword">int</span><span class="special">(*</span><span class="identifier">g</span><span class="special">)(</span><span class="keyword">int</span><span class="special">,</span><span class="keyword">double</span><span class="special">,</span><span class="keyword">char</span> <span class="keyword">const</span><span class="special">*)</span> <span class="special">=</span> <span class="identifier">f</span><span class="special">;</span> <span class="comment">// defaults lost!
</span></pre>
<p> <p>
When we pass this function pointer to the <code class="literal">def</code> function, When we pass this function pointer to the <tt class="literal">def</tt> function,
there is no way to retrieve the default arguments: there is no way to retrieve the default arguments:
</p> </p>
<pre class="programlisting"><span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">f</span><span class="special">);</span> <span class="comment">// defaults lost!</span> <pre class="programlisting">
</pre> <span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">f</span><span class="special">);</span> <span class="comment">// defaults lost!
</span></pre>
<p> <p>
Because of this, when wrapping C++ code, we had to resort to manual wrapping Because of this, when wrapping C++ code, we had to resort to manual wrapping
as outlined in the <a class="link" href="functions.html#python.overloading" title="Overloading">previous section</a>, as outlined in the <a href="functions.html#python.overloading" title="Overloading">previous section</a>,
or writing thin wrappers: or writing thin wrappers:
</p> </p>
<pre class="programlisting"><span class="comment">// write "thin wrappers"</span> <pre class="programlisting">
<span class="keyword">int</span> <span class="identifier">f1</span><span class="special">(</span><span class="keyword">int</span> <span class="identifier">x</span><span class="special">)</span> <span class="special">{</span> <span class="keyword">return</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">x</span><span class="special">);</span> <span class="special">}</span> <span class="comment">// write "thin wrappers"
<span class="keyword">int</span> <span class="identifier">f2</span><span class="special">(</span><span class="keyword">int</span> <span class="identifier">x</span><span class="special">,</span> <span class="keyword">double</span> <span class="identifier">y</span><span class="special">)</span> <span class="special">{</span> <span class="keyword">return</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">x</span><span class="special">,</span><span class="identifier">y</span><span class="special">);</span> <span class="special">}</span> </span><span class="keyword">int</span> <span class="identifier">f1</span><span class="special">(</span><span class="keyword">int</span> <span class="identifier">x</span><span class="special">)</span> <span class="special">{</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">x</span><span class="special">);</span> <span class="special">}</span>
<span class="keyword">int</span> <span class="identifier">f2</span><span class="special">(</span><span class="keyword">int</span> <span class="identifier">x</span><span class="special">,</span> <span class="keyword">double</span> <span class="identifier">y</span><span class="special">)</span> <span class="special">{</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">x</span><span class="special">,</span><span class="identifier">y</span><span class="special">);</span> <span class="special">}</span>
<span class="comment">/*...*/</span> <span class="comment">/*...*/</span>
<span class="comment">// in module init</span> <span class="comment">// in module init
<span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">f</span><span class="special">);</span> <span class="comment">// all arguments</span> </span> <span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">f</span><span class="special">);</span> <span class="comment">// all arguments
<span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">f2</span><span class="special">);</span> <span class="comment">// two arguments</span> </span> <span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">f2</span><span class="special">);</span> <span class="comment">// two arguments
<span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">f1</span><span class="special">);</span> <span class="comment">// one argument</span> </span> <span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">f1</span><span class="special">);</span> <span class="comment">// one argument
</pre> </span></pre>
<p> <p>
When you want to wrap functions (or member functions) that either: When you want to wrap functions (or member functions) that either:
</p> </p>
<div class="itemizedlist"><ul class="itemizedlist" type="disc"> <div class="itemizedlist"><ul type="disc">
<li class="listitem"> <li>
have default arguments, or have default arguments, or
</li> </li>
<li class="listitem"> <li>
are overloaded with a common sequence of initial arguments are overloaded with a common sequence of initial arguments
</li> </li>
</ul></div> </ul></div>
<h3> <a name="default_arguments.boost_python_function_overloads"></a><h2>
<a name="default_arguments.boost_python_function_overloads"></a> <a name="id466117"></a>
BOOST_PYTHON_FUNCTION_OVERLOADS BOOST_PYTHON_FUNCTION_OVERLOADS
</h3> </h2>
<p> <p>
Boost.Python now has a way to make it easier. For instance, given a function: Boost.Python now has a way to make it easier. For instance, given a function:
</p> </p>
<pre class="programlisting"><span class="keyword">int</span> <span class="identifier">foo</span><span class="special">(</span><span class="keyword">int</span> <span class="identifier">a</span><span class="special">,</span> <span class="keyword">char</span> <span class="identifier">b</span> <span class="special">=</span> <span class="number">1</span><span class="special">,</span> <span class="keyword">unsigned</span> <span class="identifier">c</span> <span class="special">=</span> <span class="number">2</span><span class="special">,</span> <span class="keyword">double</span> <span class="identifier">d</span> <span class="special">=</span> <span class="number">3</span><span class="special">)</span> <pre class="programlisting">
<span class="keyword">int</span> <span class="identifier">foo</span><span class="special">(</span><span class="keyword">int</span> <span class="identifier">a</span><span class="special">,</span> <span class="keyword">char</span> <span class="identifier">b</span> <span class="special">=</span> <span class="number">1</span><span class="special">,</span> <span class="keyword">unsigned</span> <span class="identifier">c</span> <span class="special">=</span> <span class="number">2</span><span class="special">,</span> <span class="keyword">double</span> <span class="identifier">d</span> <span class="special">=</span> <span class="number">3</span><span class="special">)</span>
<span class="special">{</span> <span class="special">{</span>
<span class="comment">/*...*/</span> <span class="comment">/*...*/</span>
<span class="special">}</span> <span class="special">}</span>
@@ -408,22 +430,24 @@ Namespaces are one honking great idea -- let's do more of those!
<p> <p>
The macro invocation: The macro invocation:
</p> </p>
<pre class="programlisting"><span class="identifier">BOOST_PYTHON_FUNCTION_OVERLOADS</span><span class="special">(</span><span class="identifier">foo_overloads</span><span class="special">,</span> <span class="identifier">foo</span><span class="special">,</span> <span class="number">1</span><span class="special">,</span> <span class="number">4</span><span class="special">)</span> <pre class="programlisting">
<span class="identifier">BOOST_PYTHON_FUNCTION_OVERLOADS</span><span class="special">(</span><span class="identifier">foo_overloads</span><span class="special">,</span> <span class="identifier">foo</span><span class="special">,</span> <span class="number">1</span><span class="special">,</span> <span class="number">4</span><span class="special">)</span>
</pre> </pre>
<p> <p>
will automatically create the thin wrappers for us. This macro will create will automatically create the thin wrappers for us. This macro will create
a class <code class="literal">foo_overloads</code> that can be passed on to <code class="literal">def(...)</code>. a class <tt class="literal">foo_overloads</tt> that can be passed on to <tt class="literal">def(...)</tt>.
The third and fourth macro argument are the minimum arguments and maximum The third and fourth macro argument are the minimum arguments and maximum
arguments, respectively. In our <code class="literal">foo</code> function the minimum arguments, respectively. In our <tt class="literal">foo</tt> function the minimum
number of arguments is 1 and the maximum number of arguments is 4. The <code class="literal">def(...)</code> number of arguments is 1 and the maximum number of arguments is 4. The <tt class="literal">def(...)</tt>
function will automatically add all the foo variants for us: function will automatically add all the foo variants for us:
</p> </p>
<pre class="programlisting"><span class="identifier">def</span><span class="special">(</span><span class="string">"foo"</span><span class="special">,</span> <span class="identifier">foo</span><span class="special">,</span> <span class="identifier">foo_overloads</span><span class="special">());</span> <pre class="programlisting">
<span class="identifier">def</span><span class="special">(</span><span class="string">"foo"</span><span class="special">,</span> <span class="identifier">foo</span><span class="special">,</span> <span class="identifier">foo_overloads</span><span class="special">());</span>
</pre> </pre>
<h3> <a name="default_arguments.boost_python_member_function_overloads"></a><h2>
<a name="default_arguments.boost_python_member_function_overloads"></a> <a name="id466436"></a>
BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS
</h3> </h2>
<p> <p>
Objects here, objects there, objects here there everywhere. More frequently Objects here, objects there, objects here there everywhere. More frequently
than anything else, we need to expose member functions of our classes to than anything else, we need to expose member functions of our classes to
@@ -432,11 +456,12 @@ Namespaces are one honking great idea -- let's do more of those!
play. Another macro is provided to make this a breeze. play. Another macro is provided to make this a breeze.
</p> </p>
<p> <p>
Like <code class="literal">BOOST_PYTHON_FUNCTION_OVERLOADS</code>, <code class="literal">BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS</code> Like <tt class="literal">BOOST_PYTHON_FUNCTION_OVERLOADS</tt>, <tt class="literal">BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS</tt>
may be used to automatically create the thin wrappers for wrapping member may be used to automatically create the thin wrappers for wrapping member
functions. Let's have an example: functions. Let's have an example:
</p> </p>
<pre class="programlisting"><span class="keyword">struct</span> <span class="identifier">george</span> <pre class="programlisting">
<span class="keyword">struct</span> <span class="identifier">george</span>
<span class="special">{</span> <span class="special">{</span>
<span class="keyword">void</span> <span class="keyword">void</span>
<span class="identifier">wack_em</span><span class="special">(</span><span class="keyword">int</span> <span class="identifier">a</span><span class="special">,</span> <span class="keyword">int</span> <span class="identifier">b</span> <span class="special">=</span> <span class="number">0</span><span class="special">,</span> <span class="keyword">char</span> <span class="identifier">c</span> <span class="special">=</span> <span class="char">'x'</span><span class="special">)</span> <span class="identifier">wack_em</span><span class="special">(</span><span class="keyword">int</span> <span class="identifier">a</span><span class="special">,</span> <span class="keyword">int</span> <span class="identifier">b</span> <span class="special">=</span> <span class="number">0</span><span class="special">,</span> <span class="keyword">char</span> <span class="identifier">c</span> <span class="special">=</span> <span class="char">'x'</span><span class="special">)</span>
@@ -448,31 +473,34 @@ Namespaces are one honking great idea -- let's do more of those!
<p> <p>
The macro invocation: The macro invocation:
</p> </p>
<pre class="programlisting"><span class="identifier">BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS</span><span class="special">(</span><span class="identifier">george_overloads</span><span class="special">,</span> <span class="identifier">wack_em</span><span class="special">,</span> <span class="number">1</span><span class="special">,</span> <span class="number">3</span><span class="special">)</span> <pre class="programlisting">
<span class="identifier">BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS</span><span class="special">(</span><span class="identifier">george_overloads</span><span class="special">,</span> <span class="identifier">wack_em</span><span class="special">,</span> <span class="number">1</span><span class="special">,</span> <span class="number">3</span><span class="special">)</span>
</pre> </pre>
<p> <p>
will generate a set of thin wrappers for george's <code class="literal">wack_em</code> will generate a set of thin wrappers for george's <tt class="literal">wack_em</tt>
member function accepting a minimum of 1 and a maximum of 3 arguments (i.e. member function accepting a minimum of 1 and a maximum of 3 arguments (i.e.
the third and fourth macro argument). The thin wrappers are all enclosed the third and fourth macro argument). The thin wrappers are all enclosed
in a class named <code class="literal">george_overloads</code> that can then be used in a class named <tt class="literal">george_overloads</tt> that can then be used
as an argument to <code class="literal">def(...)</code>: as an argument to <tt class="literal">def(...)</tt>:
</p> </p>
<pre class="programlisting"><span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"wack_em"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">george</span><span class="special">::</span><span class="identifier">wack_em</span><span class="special">,</span> <span class="identifier">george_overloads</span><span class="special">());</span> <pre class="programlisting">
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"wack_em"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">george</span><span class="special">::</span><span class="identifier">wack_em</span><span class="special">,</span> <span class="identifier">george_overloads</span><span class="special">());</span>
</pre> </pre>
<p> <p>
See the <a href="../../../../v2/overloads.html#BOOST_PYTHON_FUNCTION_OVERLOADS-spec" target="_top">overloads See the <a href="../../../../v2/overloads.html#BOOST_PYTHON_FUNCTION_OVERLOADS-spec" target="_top">overloads
reference</a> for details. reference</a> for details.
</p> </p>
<h3> <a name="default_arguments.init_and_optional"></a><h2>
<a name="default_arguments.init_and_optional"></a> <a name="id466799"></a>
init and optional init and optional
</h3> </h2>
<p> <p>
A similar facility is provided for class constructors, again, with default A similar facility is provided for class constructors, again, with default
arguments or a sequence of overloads. Remember <code class="literal">init&lt;...&gt;</code>? arguments or a sequence of overloads. Remember <tt class="literal">init&lt;...&gt;</tt>?
For example, given a class X with a constructor: For example, given a class X with a constructor:
</p> </p>
<pre class="programlisting"><span class="keyword">struct</span> <span class="identifier">X</span> <pre class="programlisting">
<span class="keyword">struct</span> <span class="identifier">X</span>
<span class="special">{</span> <span class="special">{</span>
<span class="identifier">X</span><span class="special">(</span><span class="keyword">int</span> <span class="identifier">a</span><span class="special">,</span> <span class="keyword">char</span> <span class="identifier">b</span> <span class="special">=</span> <span class="char">'D'</span><span class="special">,</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">c</span> <span class="special">=</span> <span class="string">"constructor"</span><span class="special">,</span> <span class="keyword">double</span> <span class="identifier">d</span> <span class="special">=</span> <span class="number">0.0</span><span class="special">);</span> <span class="identifier">X</span><span class="special">(</span><span class="keyword">int</span> <span class="identifier">a</span><span class="special">,</span> <span class="keyword">char</span> <span class="identifier">b</span> <span class="special">=</span> <span class="char">'D'</span><span class="special">,</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">c</span> <span class="special">=</span> <span class="string">"constructor"</span><span class="special">,</span> <span class="keyword">double</span> <span class="identifier">d</span> <span class="special">=</span> <span class="number">0.0</span><span class="special">);</span>
<span class="comment">/*...*/</span> <span class="comment">/*...*/</span>
@@ -481,23 +509,25 @@ Namespaces are one honking great idea -- let's do more of those!
<p> <p>
You can easily add this constructor to Boost.Python in one shot: You can easily add this constructor to Boost.Python in one shot:
</p> </p>
<pre class="programlisting"><span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">init</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">,</span> <span class="identifier">optional</span><span class="special">&lt;</span><span class="keyword">char</span><span class="special">,</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span><span class="special">,</span> <span class="keyword">double</span><span class="special">&gt;</span> <span class="special">&gt;())</span> <pre class="programlisting">
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="identifier">init</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">,</span> <span class="identifier">optional</span><span class="special">&lt;</span><span class="keyword">char</span><span class="special">,</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span><span class="special">,</span> <span class="keyword">double</span><span class="special">&gt;</span> <span class="special">&gt;())</span>
</pre> </pre>
<p> <p>
Notice the use of <code class="literal">init&lt;...&gt;</code> and <code class="literal">optional&lt;...&gt;</code> Notice the use of <tt class="literal">init&lt;...&gt;</tt> and <tt class="literal">optional&lt;...&gt;</tt>
to signify the default (optional arguments). to signify the default (optional arguments).
</p> </p>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h3 class="title"> <div class="titlepage"><div><div><h3 class="title">
<a name="python.auto_overloading"></a>Auto-Overloading</h3></div></div></div> <a name="python.auto_overloading"></a>Auto-Overloading</h3></div></div></div>
<p> <p>
It was mentioned in passing in the previous section that <code class="literal">BOOST_PYTHON_FUNCTION_OVERLOADS</code> It was mentioned in passing in the previous section that <tt class="literal">BOOST_PYTHON_FUNCTION_OVERLOADS</tt>
and <code class="literal">BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS</code> can also be and <tt class="literal">BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS</tt> can also be
used for overloaded functions and member functions with a common sequence used for overloaded functions and member functions with a common sequence
of initial arguments. Here is an example: of initial arguments. Here is an example:
</p> </p>
<pre class="programlisting"><span class="keyword">void</span> <span class="identifier">foo</span><span class="special">()</span> <pre class="programlisting">
<span class="keyword">void</span> <span class="identifier">foo</span><span class="special">()</span>
<span class="special">{</span> <span class="special">{</span>
<span class="comment">/*...*/</span> <span class="comment">/*...*/</span>
<span class="special">}</span> <span class="special">}</span>
@@ -521,56 +551,61 @@ Namespaces are one honking great idea -- let's do more of those!
Like in the previous section, we can generate thin wrappers for these overloaded Like in the previous section, we can generate thin wrappers for these overloaded
functions in one-shot: functions in one-shot:
</p> </p>
<pre class="programlisting"><span class="identifier">BOOST_PYTHON_FUNCTION_OVERLOADS</span><span class="special">(</span><span class="identifier">foo_overloads</span><span class="special">,</span> <span class="identifier">foo</span><span class="special">,</span> <span class="number">0</span><span class="special">,</span> <span class="number">3</span><span class="special">)</span> <pre class="programlisting">
<span class="identifier">BOOST_PYTHON_FUNCTION_OVERLOADS</span><span class="special">(</span><span class="identifier">foo_overloads</span><span class="special">,</span> <span class="identifier">foo</span><span class="special">,</span> <span class="number">0</span><span class="special">,</span> <span class="number">3</span><span class="special">)</span>
</pre> </pre>
<p> <p>
Then... Then...
</p> </p>
<pre class="programlisting"><span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"foo"</span><span class="special">,</span> <span class="special">(</span><span class="keyword">void</span><span class="special">(*)(</span><span class="keyword">bool</span><span class="special">,</span> <span class="keyword">int</span><span class="special">,</span> <span class="keyword">char</span><span class="special">))</span><span class="number">0</span><span class="special">,</span> <span class="identifier">foo_overloads</span><span class="special">());</span> <pre class="programlisting">
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"foo"</span><span class="special">,</span> <span class="special">(</span><span class="keyword">void</span><span class="special">(*)(</span><span class="keyword">bool</span><span class="special">,</span> <span class="keyword">int</span><span class="special">,</span> <span class="keyword">char</span><span class="special">))</span><span class="number">0</span><span class="special">,</span> <span class="identifier">foo_overloads</span><span class="special">());</span>
</pre> </pre>
<p> <p>
Notice though that we have a situation now where we have a minimum of zero Notice though that we have a situation now where we have a minimum of zero
(0) arguments and a maximum of 3 arguments. (0) arguments and a maximum of 3 arguments.
</p> </p>
<h3> <a name="auto_overloading.manual_wrapping"></a><h2>
<a name="auto_overloading.manual_wrapping"></a> <a name="id467581"></a>
Manual Wrapping Manual Wrapping
</h3> </h2>
<p> <p>
It is important to emphasize however that <span class="bold"><strong>the overloaded It is important to emphasize however that <span class="bold"><b>the overloaded
functions must have a common sequence of initial arguments</strong></span>. Otherwise, functions must have a common sequence of initial arguments</b></span>. Otherwise,
our scheme above will not work. If this is not the case, we have to wrap our scheme above will not work. If this is not the case, we have to wrap
our functions <a class="link" href="functions.html#python.overloading" title="Overloading">manually</a>. our functions <a href="functions.html#python.overloading" title="Overloading">manually</a>.
</p> </p>
<p> <p>
Actually, we can mix and match manual wrapping of overloaded functions and Actually, we can mix and match manual wrapping of overloaded functions and
automatic wrapping through <code class="literal">BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS</code> automatic wrapping through <tt class="literal">BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS</tt>
and its sister, <code class="literal">BOOST_PYTHON_FUNCTION_OVERLOADS</code>. Following and its sister, <tt class="literal">BOOST_PYTHON_FUNCTION_OVERLOADS</tt>. Following
up on our example presented in the section <a class="link" href="functions.html#python.overloading" title="Overloading">on up on our example presented in the section <a href="functions.html#python.overloading" title="Overloading">on
overloading</a>, since the first 4 overload functins have a common sequence overloading</a>, since the first 4 overload functins have a common sequence
of initial arguments, we can use <code class="literal">BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS</code> of initial arguments, we can use <tt class="literal">BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS</tt>
to automatically wrap the first three of the <code class="literal">def</code>s and to automatically wrap the first three of the <tt class="literal">def</tt>s and
manually wrap just the last. Here's how we'll do this: manually wrap just the last. Here's how we'll do this:
</p> </p>
<pre class="programlisting"><span class="identifier">BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS</span><span class="special">(</span><span class="identifier">xf_overloads</span><span class="special">,</span> <span class="identifier">f</span><span class="special">,</span> <span class="number">1</span><span class="special">,</span> <span class="number">4</span><span class="special">)</span> <pre class="programlisting">
<span class="identifier">BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS</span><span class="special">(</span><span class="identifier">xf_overloads</span><span class="special">,</span> <span class="identifier">f</span><span class="special">,</span> <span class="number">1</span><span class="special">,</span> <span class="number">4</span><span class="special">)</span>
</pre> </pre>
<p> <p>
Create a member function pointers as above for both X::f overloads: Create a member function pointers as above for both X::f overloads:
</p> </p>
<pre class="programlisting"><span class="keyword">bool</span> <span class="special">(</span><span class="identifier">X</span><span class="special">::*</span><span class="identifier">fx1</span><span class="special">)(</span><span class="keyword">int</span><span class="special">,</span> <span class="keyword">double</span><span class="special">,</span> <span class="keyword">char</span><span class="special">)</span> <span class="special">=</span> <span class="special">&amp;</span><span class="identifier">X</span><span class="special">::</span><span class="identifier">f</span><span class="special">;</span> <pre class="programlisting">
<span class="keyword">bool</span> <span class="special">(</span><span class="identifier">X</span><span class="special">::*</span><span class="identifier">fx1</span><span class="special">)(</span><span class="keyword">int</span><span class="special">,</span> <span class="keyword">double</span><span class="special">,</span> <span class="keyword">char</span><span class="special">)</span> <span class="special">=</span> <span class="special">&amp;</span><span class="identifier">X</span><span class="special">::</span><span class="identifier">f</span><span class="special">;</span>
<span class="keyword">int</span> <span class="special">(</span><span class="identifier">X</span><span class="special">::*</span><span class="identifier">fx2</span><span class="special">)(</span><span class="keyword">int</span><span class="special">,</span> <span class="keyword">int</span><span class="special">,</span> <span class="keyword">int</span><span class="special">)</span> <span class="special">=</span> <span class="special">&amp;</span><span class="identifier">X</span><span class="special">::</span><span class="identifier">f</span><span class="special">;</span> <span class="keyword">int</span> <span class="special">(</span><span class="identifier">X</span><span class="special">::*</span><span class="identifier">fx2</span><span class="special">)(</span><span class="keyword">int</span><span class="special">,</span> <span class="keyword">int</span><span class="special">,</span> <span class="keyword">int</span><span class="special">)</span> <span class="special">=</span> <span class="special">&amp;</span><span class="identifier">X</span><span class="special">::</span><span class="identifier">f</span><span class="special">;</span>
</pre> </pre>
<p> <p>
Then... Then...
</p> </p>
<pre class="programlisting"><span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">fx1</span><span class="special">,</span> <span class="identifier">xf_overloads</span><span class="special">());</span> <pre class="programlisting">
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">fx1</span><span class="special">,</span> <span class="identifier">xf_overloads</span><span class="special">());</span>
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">fx2</span><span class="special">)</span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"f"</span><span class="special">,</span> <span class="identifier">fx2</span><span class="special">)</span>
</pre> </pre>
</div> </div>
</div> </div>
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr> <table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
<td align="left"></td> <td align="left"></td>
<td align="right"><div class="copyright-footer">Copyright &#169; 2002-2005 Joel <td align="right"><div class="copyright-footer">Copyright © 2002-2005 Joel
de Guzman, David Abrahams<p> de Guzman, David Abrahams<p>
Distributed under the Boost Software License, Version 1.0. (See accompanying Distributed under the Boost Software License, Version 1.0. (See accompanying
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top"> file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">
@@ -580,7 +615,7 @@ Namespaces are one honking great idea -- let's do more of those!
</tr></table> </tr></table>
<hr> <hr>
<div class="spirit-nav"> <div class="spirit-nav">
<a accesskey="p" href="exposing.html"><img src="../../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="object.html"><img src="../../../../../../../doc/src/images/next.png" alt="Next"></a> <a accesskey="p" href="exposing.html"><img src="../../../../../../../doc/html/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/html/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/html/images/home.png" alt="Home"></a><a accesskey="n" href="object.html"><img src="../../../../../../../doc/html/images/next.png" alt="Next"></a>
</div> </div>
</body> </body>
</html> </html>

View File

@@ -1,53 +1,53 @@
<html> <html>
<head> <head>
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII"> <meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
<title>Building Hello World</title> <title> Building Hello World</title>
<link rel="stylesheet" href="../../../../../../../doc/src/boostbook.css" type="text/css"> <link rel="stylesheet" href="../../../../../../../doc/html/boostbook.css" type="text/css">
<meta name="generator" content="DocBook XSL Stylesheets V1.76.1"> <meta name="generator" content="DocBook XSL Stylesheets V1.66.1">
<link rel="home" href="../index.html" title="Chapter&#160;1.&#160;python 2.0"> <link rel="start" href="../index.html" title="Chapter 1. python 1.0">
<link rel="up" href="../index.html" title="Chapter&#160;1.&#160;python 2.0"> <link rel="up" href="../index.html" title="Chapter 1. python 1.0">
<link rel="prev" href="../index.html" title="Chapter&#160;1.&#160;python 2.0"> <link rel="prev" href="../index.html" title="Chapter 1. python 1.0">
<link rel="next" href="exposing.html" title="Exposing Classes"> <link rel="next" href="exposing.html" title=" Exposing Classes">
</head> </head>
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"> <body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
<table cellpadding="2" width="100%"><tr> <table cellpadding="2" width="100%"><tr>
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../../boost.png"></td> <td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../../boost.png"></td>
<td align="center"><a href="../../../../../../../index.html">Home</a></td> <td align="center"><a href="../../../../../../../index.htm">Home</a></td>
<td align="center"><a href="../../../../../../../libs/libraries.htm">Libraries</a></td> <td align="center"><a href="../../../../../../../libs/libraries.htm">Libraries</a></td>
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td> <td align="center"><a href="../../../../../../../people/people.htm">People</a></td>
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td> <td align="center"><a href="../../../../../../../more/faq.htm">FAQ</a></td>
<td align="center"><a href="../../../../../../../more/index.htm">More</a></td> <td align="center"><a href="../../../../../../../more/index.htm">More</a></td>
</tr></table> </tr></table>
<hr> <hr>
<div class="spirit-nav"> <div class="spirit-nav">
<a accesskey="p" href="../index.html"><img src="../../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="exposing.html"><img src="../../../../../../../doc/src/images/next.png" alt="Next"></a> <a accesskey="p" href="../index.html"><img src="../../../../../../../doc/html/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/html/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/html/images/home.png" alt="Home"></a><a accesskey="n" href="exposing.html"><img src="../../../../../../../doc/html/images/next.png" alt="Next"></a>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h2 class="title" style="clear: both"> <div class="titlepage"><div><div><h2 class="title" style="clear: both">
<a name="python.hello"></a>Building Hello World</h2></div></div></div> <a name="python.hello"></a> Building Hello World</h2></div></div></div>
<h3> <a name="hello.from_start_to_finish"></a><h2>
<a name="hello.from_start_to_finish"></a> <a name="id387672"></a>
From Start To Finish From Start To Finish
</h3> </h2>
<p> <p>
Now the first thing you'd want to do is to build the Hello World module and Now the first thing you'd want to do is to build the Hello World module and
try it for yourself in Python. In this section, we will outline the steps necessary try it for yourself in Python. In this section, we will outline the steps necessary
to achieve that. We will use the build tool that comes bundled with every boost to achieve that. We will use the build tool that comes bundled with every boost
distribution: <span class="bold"><strong>bjam</strong></span>. distribution: <span class="bold"><b>bjam</b></span>.
</p> </p>
<div class="note"><table border="0" summary="Note"> <div class="note"><table border="0" summary="Note">
<tr> <tr>
<td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../../../doc/src/images/note.png"></td> <td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../../../doc/html/images/note.png"></td>
<th align="left">Note</th> <th align="left">Note</th>
</tr> </tr>
<tr><td align="left" valign="top"> <tr><td colspan="2" align="left" valign="top">
<p> <p>
<span class="bold"><strong>Building without bjam</strong></span> <span class="bold"><b>Building without bjam</b></span>
</p> </p>
<p> <p>
Besides bjam, there are of course other ways to get your module built. What's Besides bjam, there are of course other ways to get your module built. What's
written here should not be taken as "the one and only way". There written here should not be taken as "the one and only way". There
are of course other build tools apart from <code class="literal">bjam</code>. are of course other build tools apart from <tt class="literal">bjam</tt>.
</p> </p>
<p> <p>
Take note however that the preferred build tool for Boost.Python is bjam. Take note however that the preferred build tool for Boost.Python is bjam.
@@ -65,59 +65,65 @@
and run a python program using the extension. and run a python program using the extension.
</p> </p>
<p> <p>
The tutorial example can be found in the directory: <code class="literal">libs/python/example/tutorial</code>. The tutorial example can be found in the directory: <tt class="literal">libs/python/example/tutorial</tt>.
There, you can find: There, you can find:
</p> </p>
<div class="itemizedlist"><ul class="itemizedlist" type="disc"> <div class="itemizedlist"><ul type="disc">
<li class="listitem"> <li>
hello.cpp hello.cpp
</li> </li>
<li class="listitem"> <li>
hello.py hello.py
</li> </li>
<li class="listitem"> <li>
Jamroot Jamroot
</li> </li>
</ul></div> </ul></div>
<p> <p>
The <code class="literal">hello.cpp</code> file is our C++ hello world example. The The <tt class="literal">hello.cpp</tt> file is our C++ hello world example. The
<code class="literal">Jamroot</code> is a minimalist <span class="emphasis"><em>bjam</em></span> script <tt class="literal">Jamroot</tt> is a minimalist <span class="emphasis"><em>bjam</em></span> script
that builds the DLLs for us. Finally, <code class="literal">hello.py</code> is our Python that builds the DLLs for us. Finally, <tt class="literal">hello.py</tt> is our Python
program that uses the extension in <code class="literal">hello.cpp</code>. program that uses the extension in <tt class="literal">hello.cpp</tt>.
</p> </p>
<p> <p>
Before anything else, you should have the bjam executable in your boost directory Before anything else, you should have the bjam executable in your boost directory
or somewhere in your path such that <code class="literal">bjam</code> can be executed or somewhere in your path such that <tt class="literal">bjam</tt> can be executed
in the command line. Pre-built Boost.Jam executables are available for most in the command line. Pre-built Boost.Jam executables are available for most
platforms. The complete list of Bjam executables can be found <a href="http://sourceforge.net/project/showfiles.php?group_id=7586" target="_top">here</a>. platforms. The complete list of Bjam executables can be found <a href="http://sourceforge.net/project/showfiles.php?group_id=7586" target="_top">here</a>.
</p> </p>
<h3> <a name="hello.let_s_jam_"></a><h2>
<a name="hello.let_s_jam_"></a> <a name="id386265"></a>
Let's Jam! Let's Jam!
</h3> </h2>
<p> <p>
<span class="inlinemediaobject"><img src="../images/jam.png" alt="jam"></span> <span class="inlinemediaobject"><img src="../images/jam.png" alt="jam"></span>
</p> </p>
<p> <p>
<a href="../../../../../example/tutorial/Jamroot" target="_top">Here</a> is our minimalist <a href="../../../../../example/tutorial/Jamroot" target="_top">Here</a> is our minimalist
Jamroot file. Simply copy the file and tweak <code class="literal">use-project boost</code> Jamroot file. Simply copy the file and tweak <tt class="literal">use-project boost</tt>
to where your boost root directory is and your OK. to where your boost root directory is and your OK.
</p> </p>
<p> <p>
The comments contained in the Jamrules file above should be sufficient to get The comments contained in the Jamrules file above should be sufficient to get
you going. you going.
</p> </p>
<h3> <a name="hello.running_bjam"></a><h2>
<a name="hello.running_bjam"></a> <a name="id386322"></a>
Running bjam Running bjam
</h3> </h2>
<p> <p>
<span class="emphasis"><em>bjam</em></span> is run using your operating system's command line <span class="emphasis"><em>bjam</em></span> is run using your operating system's command line
interpreter. interpreter.
</p> </p>
<div class="blockquote"><blockquote class="blockquote"><p> <div class="blockquote"><blockquote class="blockquote">
Start it up. <p>
</p></blockquote></div> </p>
<p>
Start it up.
</p>
<p>
</p>
</blockquote></div>
<p> <p>
A file called user-config.jam in your home directory is used to configure your A file called user-config.jam in your home directory is used to configure your
tools. In Windows, your home directory can be found by typing: tools. In Windows, your home directory can be found by typing:
@@ -133,24 +139,25 @@
using msvc : 8.0 ; using msvc : 8.0 ;
# Python configuration # Python configuration
using python : 2.4 : C:<span class="emphasis"><em>dev/tools/Python</em></span> ; using python : 2.4 : C:/dev/tools<span class="emphasis"><em>Python</em></span> ;
</pre> </pre>
<p> <p>
The first rule tells Bjam to use the MSVC 8.0 compiler and associated tools. The first rule tells Bjam to use the MSVC 8.0 compiler and associated tools.
The second rule provides information on Python, its version and where it is The second rule provides information on Python, its version and where it is
located. The above assumes that the Python installation is in <code class="literal">C:<span class="emphasis"><em>dev/tools\/Python</em></span></code>. located. The above assumes that the Python installation is in <tt class="literal">C:/dev/tools/Python/</tt>.
If you have one fairly "standard" python installation for your platform, If you have one fairly "standard" python installation for your platform,
you might not need to do this. you might not need to do this.
</p> </p>
<p> <p>
Now we are ready... Be sure to <code class="literal">cd</code> to <code class="literal">libs/python/example/tutorial</code> Now we are ready... Be sure to <tt class="literal">cd</tt> to <tt class="literal">libs/python/example/tutorial</tt>
where the tutorial <code class="literal">"hello.cpp"</code> and the <code class="literal">"Jamroot"</code> where the tutorial <tt class="literal">"hello.cpp"</tt> and the <tt class="literal">"Jamroot"</tt>
is situated. is situated.
</p> </p>
<p> <p>
Finally: Finally:
</p> </p>
<pre class="programlisting"><span class="identifier">bjam</span> <pre class="programlisting">
<span class="identifier">bjam</span>
</pre> </pre>
<p> <p>
It should be building now: It should be building now:
@@ -165,7 +172,7 @@ bjam
And so on... Finally: And so on... Finally:
</p> </p>
<pre class="programlisting">Creating library <span class="emphasis"><em>path-to-boost_python.dll</em></span> <pre class="programlisting">Creating library <span class="emphasis"><em>path-to-boost_python.dll</em></span>
Creating library /path-to-hello_ext.exp/ Creating library <span class="emphasis"><em>path-to-'''hello_ext'''.exp</em></span>
**passed** ... hello.test **passed** ... hello.test
...updated 35 targets... ...updated 35 targets...
</pre> </pre>
@@ -173,13 +180,19 @@ bjam
Or something similar. If all is well, you should now have built the DLLs and Or something similar. If all is well, you should now have built the DLLs and
run the Python program. run the Python program.
</p> </p>
<div class="blockquote"><blockquote class="blockquote"><p> <div class="blockquote"><blockquote class="blockquote">
<span class="bold"><strong>There you go... Have fun!</strong></span> <p>
</p></blockquote></div> </p>
<p>
<span class="bold"><b>There you go... Have fun!</b></span>
</p>
<p>
</p>
</blockquote></div>
</div> </div>
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr> <table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
<td align="left"></td> <td align="left"></td>
<td align="right"><div class="copyright-footer">Copyright &#169; 2002-2005 Joel <td align="right"><div class="copyright-footer">Copyright © 2002-2005 Joel
de Guzman, David Abrahams<p> de Guzman, David Abrahams<p>
Distributed under the Boost Software License, Version 1.0. (See accompanying Distributed under the Boost Software License, Version 1.0. (See accompanying
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top"> file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">
@@ -189,7 +202,7 @@ bjam
</tr></table> </tr></table>
<hr> <hr>
<div class="spirit-nav"> <div class="spirit-nav">
<a accesskey="p" href="../index.html"><img src="../../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="exposing.html"><img src="../../../../../../../doc/src/images/next.png" alt="Next"></a> <a accesskey="p" href="../index.html"><img src="../../../../../../../doc/html/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/html/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/html/images/home.png" alt="Home"></a><a accesskey="n" href="exposing.html"><img src="../../../../../../../doc/html/images/next.png" alt="Next"></a>
</div> </div>
</body> </body>
</html> </html>

View File

@@ -1,28 +1,28 @@
<html> <html>
<head> <head>
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII"> <meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
<title>Iterators</title> <title>Iterators</title>
<link rel="stylesheet" href="../../../../../../../doc/src/boostbook.css" type="text/css"> <link rel="stylesheet" href="../../../../../../../doc/html/boostbook.css" type="text/css">
<meta name="generator" content="DocBook XSL Stylesheets V1.76.1"> <meta name="generator" content="DocBook XSL Stylesheets V1.66.1">
<link rel="home" href="../index.html" title="Chapter&#160;1.&#160;python 2.0"> <link rel="start" href="../index.html" title="Chapter 1. python 1.0">
<link rel="up" href="../index.html" title="Chapter&#160;1.&#160;python 2.0"> <link rel="up" href="../index.html" title="Chapter 1. python 1.0">
<link rel="prev" href="embedding.html" title="Embedding"> <link rel="prev" href="embedding.html" title="Embedding">
<link rel="next" href="exception.html" title="Exception Translation"> <link rel="next" href="exception.html" title=" Exception Translation">
</head> </head>
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"> <body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
<table cellpadding="2" width="100%"><tr> <table cellpadding="2" width="100%"><tr>
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../../boost.png"></td> <td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../../boost.png"></td>
<td align="center"><a href="../../../../../../../index.html">Home</a></td> <td align="center"><a href="../../../../../../../index.htm">Home</a></td>
<td align="center"><a href="../../../../../../../libs/libraries.htm">Libraries</a></td> <td align="center"><a href="../../../../../../../libs/libraries.htm">Libraries</a></td>
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td> <td align="center"><a href="../../../../../../../people/people.htm">People</a></td>
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td> <td align="center"><a href="../../../../../../../more/faq.htm">FAQ</a></td>
<td align="center"><a href="../../../../../../../more/index.htm">More</a></td> <td align="center"><a href="../../../../../../../more/index.htm">More</a></td>
</tr></table> </tr></table>
<hr> <hr>
<div class="spirit-nav"> <div class="spirit-nav">
<a accesskey="p" href="embedding.html"><img src="../../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="exception.html"><img src="../../../../../../../doc/src/images/next.png" alt="Next"></a> <a accesskey="p" href="embedding.html"><img src="../../../../../../../doc/html/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/html/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/html/images/home.png" alt="Home"></a><a accesskey="n" href="exception.html"><img src="../../../../../../../doc/html/images/next.png" alt="Next"></a>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h2 class="title" style="clear: both"> <div class="titlepage"><div><div><h2 class="title" style="clear: both">
<a name="python.iterators"></a>Iterators</h2></div></div></div> <a name="python.iterators"></a>Iterators</h2></div></div></div>
<p> <p>
@@ -30,102 +30,112 @@
iterators, but these are two very different beasts. iterators, but these are two very different beasts.
</p> </p>
<p> <p>
<span class="bold"><strong>C++ iterators:</strong></span> <span class="bold"><b>C++ iterators:</b></span>
</p> </p>
<div class="itemizedlist"><ul class="itemizedlist" type="disc"> <div class="itemizedlist"><ul type="disc">
<li class="listitem"> <li>
C++ has 5 type categories (random-access, bidirectional, forward, input, C++ has 5 type categories (random-access, bidirectional, forward, input,
output) output)
</li> </li>
<li class="listitem"> <li>
There are 2 Operation categories: reposition, access There are 2 Operation categories: reposition, access
</li> </li>
<li class="listitem"> <li>
A pair of iterators is needed to represent a (first/last) range. A pair of iterators is needed to represent a (first/last) range.
</li> </li>
</ul></div> </ul></div>
<p> <p>
<span class="bold"><strong>Python Iterators:</strong></span> <span class="bold"><b>Python Iterators:</b></span>
</p> </p>
<div class="itemizedlist"><ul class="itemizedlist" type="disc"> <div class="itemizedlist"><ul type="disc">
<li class="listitem"> <li>
1 category (forward) 1 category (forward)
</li> </li>
<li class="listitem"> <li>
1 operation category (next()) 1 operation category (next())
</li> </li>
<li class="listitem"> <li>
Raises StopIteration exception at end Raises StopIteration exception at end
</li> </li>
</ul></div> </ul></div>
<p> <p>
The typical Python iteration protocol: <code class="literal"><span class="bold"><strong>for y The typical Python iteration protocol: <tt class="literal"><span class="bold"><b>for y
in x...</strong></span></code> is as follows: in x...</b></span></tt> is as follows:
</p> </p>
<pre class="programlisting"><span class="identifier">iter</span> <span class="special">=</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">__iter__</span><span class="special">()</span> <span class="comment"># get iterator</span> <p>
<span class="keyword">try</span><span class="special">:</span> </p>
<pre class="programlisting">
<span class="identifier">iter</span> <span class="special">=</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">__iter__</span><span class="special">()</span> <span class="comment"># get iterator
</span><span class="keyword">try</span><span class="special">:</span>
<span class="keyword">while</span> <span class="number">1</span><span class="special">:</span> <span class="keyword">while</span> <span class="number">1</span><span class="special">:</span>
<span class="identifier">y</span> <span class="special">=</span> <span class="identifier">iter</span><span class="special">.</span><span class="identifier">next</span><span class="special">()</span> <span class="comment"># get each item</span> <span class="identifier">y</span> <span class="special">=</span> <span class="identifier">iter</span><span class="special">.</span><span class="identifier">next</span><span class="special">()</span> <span class="comment"># get each item
<span class="special">...</span> <span class="comment"># process y</span> </span> <span class="special">...</span> <span class="comment"># process y
<span class="keyword">except</span> <span class="identifier">StopIteration</span><span class="special">:</span> <span class="keyword">pass</span> <span class="comment"># iterator exhausted</span> </span><span class="keyword">except</span> <span class="identifier">StopIteration</span><span class="special">:</span> <span class="keyword">pass</span> <span class="comment"># iterator exhausted
</pre> </span></pre>
<p> <p>
Boost.Python provides some mechanisms to make C++ iterators play along nicely Boost.Python provides some mechanisms to make C++ iterators play along nicely
as Python iterators. What we need to do is to produce appropriate <code class="computeroutput"><span class="identifier">__iter__</span></code> function from C++ iterators that as Python iterators. What we need to do is to produce appropriate <tt class="computeroutput"><span class="identifier">__iter__</span></tt> function from C++ iterators that
is compatible with the Python iteration protocol. For example: is compatible with the Python iteration protocol. For example:
</p> </p>
<pre class="programlisting"><span class="identifier">object</span> <span class="identifier">get_iterator</span> <span class="special">=</span> <span class="identifier">iterator</span><span class="special">&lt;</span><span class="identifier">vector</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;</span> <span class="special">&gt;();</span> <p>
</p>
<pre class="programlisting">
<span class="identifier">object</span> <span class="identifier">get_iterator</span> <span class="special">=</span> <span class="identifier">iterator</span><span class="special">&lt;</span><span class="identifier">vector</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;</span> <span class="special">&gt;();</span>
<span class="identifier">object</span> <span class="identifier">iter</span> <span class="special">=</span> <span class="identifier">get_iterator</span><span class="special">(</span><span class="identifier">v</span><span class="special">);</span> <span class="identifier">object</span> <span class="identifier">iter</span> <span class="special">=</span> <span class="identifier">get_iterator</span><span class="special">(</span><span class="identifier">v</span><span class="special">);</span>
<span class="identifier">object</span> <span class="identifier">first</span> <span class="special">=</span> <span class="identifier">iter</span><span class="special">.</span><span class="identifier">next</span><span class="special">();</span> <span class="identifier">object</span> <span class="identifier">first</span> <span class="special">=</span> <span class="identifier">iter</span><span class="special">.</span><span class="identifier">next</span><span class="special">();</span>
</pre> </pre>
<p> <p>
Or for use in class_&lt;&gt;: Or for use in class_&lt;&gt;:
</p> </p>
<pre class="programlisting"><span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"__iter__"</span><span class="special">,</span> <span class="identifier">iterator</span><span class="special">&lt;</span><span class="identifier">vector</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;</span> <span class="special">&gt;())</span> <pre class="programlisting">
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"__iter__"</span><span class="special">,</span> <span class="identifier">iterator</span><span class="special">&lt;</span><span class="identifier">vector</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;</span> <span class="special">&gt;())</span>
</pre> </pre>
<p> <p>
<span class="bold"><strong>range</strong></span> <span class="bold"><b>range</b></span>
</p> </p>
<p> <p>
We can create a Python savvy iterator using the range function: We can create a Python savvy iterator using the range function:
</p> </p>
<div class="itemizedlist"><ul class="itemizedlist" type="disc"> <div class="itemizedlist"><ul type="disc">
<li class="listitem"> <li>
range(start, finish) range(start, finish)
</li> </li>
<li class="listitem"> <li>
range&lt;Policies,Target&gt;(start, finish) range&lt;Policies,Target&gt;(start, finish)
</li> </li>
</ul></div> </ul></div>
<p> <p>
Here, start/finish may be one of: Here, start/finish may be one of:
</p> </p>
<div class="itemizedlist"><ul class="itemizedlist" type="disc"> <div class="itemizedlist"><ul type="disc">
<li class="listitem"> <li>
member data pointers member data pointers
</li> </li>
<li class="listitem"> <li>
member function pointers member function pointers
</li> </li>
<li class="listitem"> <li>
adaptable function object (use Target parameter) adaptable function object (use Target parameter)
</li> </li>
</ul></div> </ul></div>
<p> <p>
<span class="bold"><strong>iterator</strong></span> <span class="bold"><b>iterator</b></span>
</p> </p>
<div class="itemizedlist"><ul class="itemizedlist" type="disc"><li class="listitem"> <div class="itemizedlist"><ul type="disc"><li>
iterator&lt;T, Policies&gt;() iterator&lt;T, Policies&gt;()
</li></ul></div> </li></ul></div>
<p> <p>
Given a container <code class="literal">T</code>, iterator is a shortcut that simply Given a container <tt class="literal">T</tt>, iterator is a shortcut that simply
calls <code class="literal">range</code> with &amp;T::begin, &amp;T::end. calls <tt class="literal">range</tt> with &amp;T::begin, &amp;T::end.
</p> </p>
<p> <p>
Let's put this into action... Here's an example from some hypothetical bogon Let's put this into action... Here's an example from some hypothetical bogon
Particle accelerator code: Particle accelerator code:
</p> </p>
<pre class="programlisting"><span class="identifier">f</span> <span class="special">=</span> <span class="identifier">Field</span><span class="special">()</span> <p>
</p>
<pre class="programlisting">
<span class="identifier">f</span> <span class="special">=</span> <span class="identifier">Field</span><span class="special">()</span>
<span class="keyword">for</span> <span class="identifier">x</span> <span class="keyword">in</span> <span class="identifier">f</span><span class="special">.</span><span class="identifier">pions</span><span class="special">:</span> <span class="keyword">for</span> <span class="identifier">x</span> <span class="keyword">in</span> <span class="identifier">f</span><span class="special">.</span><span class="identifier">pions</span><span class="special">:</span>
<span class="identifier">smash</span><span class="special">(</span><span class="identifier">x</span><span class="special">)</span> <span class="identifier">smash</span><span class="special">(</span><span class="identifier">x</span><span class="special">)</span>
<span class="keyword">for</span> <span class="identifier">y</span> <span class="keyword">in</span> <span class="identifier">f</span><span class="special">.</span><span class="identifier">bogons</span><span class="special">:</span> <span class="keyword">for</span> <span class="identifier">y</span> <span class="keyword">in</span> <span class="identifier">f</span><span class="special">.</span><span class="identifier">bogons</span><span class="special">:</span>
@@ -134,44 +144,53 @@
<p> <p>
Now, our C++ Wrapper: Now, our C++ Wrapper:
</p> </p>
<pre class="programlisting"><span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">F</span><span class="special">&gt;(</span><span class="string">"Field"</span><span class="special">)</span> <p>
</p>
<pre class="programlisting">
<span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">F</span><span class="special">&gt;(</span><span class="string">"Field"</span><span class="special">)</span>
<span class="special">.</span><span class="identifier">property</span><span class="special">(</span><span class="string">"pions"</span><span class="special">,</span> <span class="identifier">range</span><span class="special">(&amp;</span><span class="identifier">F</span><span class="special">::</span><span class="identifier">p_begin</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">F</span><span class="special">::</span><span class="identifier">p_end</span><span class="special">))</span> <span class="special">.</span><span class="identifier">property</span><span class="special">(</span><span class="string">"pions"</span><span class="special">,</span> <span class="identifier">range</span><span class="special">(&amp;</span><span class="identifier">F</span><span class="special">::</span><span class="identifier">p_begin</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">F</span><span class="special">::</span><span class="identifier">p_end</span><span class="special">))</span>
<span class="special">.</span><span class="identifier">property</span><span class="special">(</span><span class="string">"bogons"</span><span class="special">,</span> <span class="identifier">range</span><span class="special">(&amp;</span><span class="identifier">F</span><span class="special">::</span><span class="identifier">b_begin</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">F</span><span class="special">::</span><span class="identifier">b_end</span><span class="special">));</span> <span class="special">.</span><span class="identifier">property</span><span class="special">(</span><span class="string">"bogons"</span><span class="special">,</span> <span class="identifier">range</span><span class="special">(&amp;</span><span class="identifier">F</span><span class="special">::</span><span class="identifier">b_begin</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">F</span><span class="special">::</span><span class="identifier">b_end</span><span class="special">));</span>
</pre> </pre>
<p> <p>
<span class="bold"><strong>stl_input_iterator</strong></span> <span class="bold"><b>stl_input_iterator</b></span>
</p> </p>
<p> <p>
So far, we have seen how to expose C++ iterators and ranges to Python. Sometimes So far, we have seen how to expose C++ iterators and ranges to Python. Sometimes
we wish to go the other way, though: we'd like to pass a Python sequence to we wish to go the other way, though: we'd like to pass a Python sequence to
an STL algorithm or use it to initialize an STL container. We need to make an STL algorithm or use it to initialize an STL container. We need to make
a Python iterator look like an STL iterator. For that, we use <code class="computeroutput"><span class="identifier">stl_input_iterator</span><span class="special">&lt;&gt;</span></code>. a Python iterator look like an STL iterator. For that, we use <tt class="computeroutput"><span class="identifier">stl_input_iterator</span><span class="special">&lt;&gt;</span></tt>.
Consider how we might implement a function that exposes <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">list</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;::</span><span class="identifier">assign</span><span class="special">()</span></code> to Python: Consider how we might implement a function that exposes <tt class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">list</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;::</span><span class="identifier">assign</span><span class="special">()</span></tt> to Python:
</p> </p>
<pre class="programlisting"><span class="keyword">template</span><span class="special">&lt;</span><span class="keyword">typename</span> <span class="identifier">T</span><span class="special">&gt;</span> <p>
</p>
<pre class="programlisting">
<span class="keyword">template</span><span class="special">&lt;</span><span class="keyword">typename</span> <span class="identifier">T</span><span class="special">&gt;</span>
<span class="keyword">void</span> <span class="identifier">list_assign</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">list</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;&amp;</span> <span class="identifier">l</span><span class="special">,</span> <span class="identifier">object</span> <span class="identifier">o</span><span class="special">)</span> <span class="special">{</span> <span class="keyword">void</span> <span class="identifier">list_assign</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">list</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;&amp;</span> <span class="identifier">l</span><span class="special">,</span> <span class="identifier">object</span> <span class="identifier">o</span><span class="special">)</span> <span class="special">{</span>
<span class="comment">// Turn a Python sequence into an STL input range</span> <span class="comment">// Turn a Python sequence into an STL input range
<span class="identifier">stl_input_iterator</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;</span> <span class="identifier">begin</span><span class="special">(</span><span class="identifier">o</span><span class="special">),</span> <span class="identifier">end</span><span class="special">;</span> </span> <span class="identifier">stl_input_iterator</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;</span> <span class="identifier">begin</span><span class="special">(</span><span class="identifier">o</span><span class="special">),</span> <span class="identifier">end</span><span class="special">;</span>
<span class="identifier">l</span><span class="special">.</span><span class="identifier">assign</span><span class="special">(</span><span class="identifier">begin</span><span class="special">,</span> <span class="identifier">end</span><span class="special">);</span> <span class="identifier">l</span><span class="special">.</span><span class="identifier">assign</span><span class="special">(</span><span class="identifier">begin</span><span class="special">,</span> <span class="identifier">end</span><span class="special">);</span>
<span class="special">}</span> <span class="special">}</span>
<span class="comment">// Part of the wrapper for list&lt;int&gt;</span> <span class="comment">// Part of the wrapper for list&lt;int&gt;
<span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">list</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;</span> <span class="special">&gt;(</span><span class="string">"list_int"</span><span class="special">)</span> </span><span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">list</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;</span> <span class="special">&gt;(</span><span class="string">"list_int"</span><span class="special">)</span>
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"assign"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">list_assign</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;)</span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span><span class="string">"assign"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">list_assign</span><span class="special">&lt;</span><span class="keyword">int</span><span class="special">&gt;)</span>
<span class="comment">// ...</span> <span class="comment">// ...
<span class="special">;</span> </span> <span class="special">;</span>
</pre> </pre>
<p> <p>
Now in Python, we can assign any integer sequence to <code class="computeroutput"><span class="identifier">list_int</span></code> Now in Python, we can assign any integer sequence to <tt class="computeroutput"><span class="identifier">list_int</span></tt>
objects: objects:
</p> </p>
<pre class="programlisting"><span class="identifier">x</span> <span class="special">=</span> <span class="identifier">list_int</span><span class="special">();</span> <p>
</p>
<pre class="programlisting">
<span class="identifier">x</span> <span class="special">=</span> <span class="identifier">list_int</span><span class="special">();</span>
<span class="identifier">x</span><span class="special">.</span><span class="identifier">assign</span><span class="special">([</span><span class="number">1</span><span class="special">,</span><span class="number">2</span><span class="special">,</span><span class="number">3</span><span class="special">,</span><span class="number">4</span><span class="special">,</span><span class="number">5</span><span class="special">])</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">assign</span><span class="special">([</span><span class="number">1</span><span class="special">,</span><span class="number">2</span><span class="special">,</span><span class="number">3</span><span class="special">,</span><span class="number">4</span><span class="special">,</span><span class="number">5</span><span class="special">])</span>
</pre> </pre>
</div> </div>
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr> <table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
<td align="left"></td> <td align="left"></td>
<td align="right"><div class="copyright-footer">Copyright &#169; 2002-2005 Joel <td align="right"><div class="copyright-footer">Copyright © 2002-2005 Joel
de Guzman, David Abrahams<p> de Guzman, David Abrahams<p>
Distributed under the Boost Software License, Version 1.0. (See accompanying Distributed under the Boost Software License, Version 1.0. (See accompanying
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top"> file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">
@@ -181,7 +200,7 @@
</tr></table> </tr></table>
<hr> <hr>
<div class="spirit-nav"> <div class="spirit-nav">
<a accesskey="p" href="embedding.html"><img src="../../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="exception.html"><img src="../../../../../../../doc/src/images/next.png" alt="Next"></a> <a accesskey="p" href="embedding.html"><img src="../../../../../../../doc/html/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/html/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/html/images/home.png" alt="Home"></a><a accesskey="n" href="exception.html"><img src="../../../../../../../doc/html/images/next.png" alt="Next"></a>
</div> </div>
</body> </body>
</html> </html>

View File

@@ -1,67 +1,69 @@
<html> <html>
<head> <head>
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII"> <meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
<title>Object Interface</title> <title> Object Interface</title>
<link rel="stylesheet" href="../../../../../../../doc/src/boostbook.css" type="text/css"> <link rel="stylesheet" href="../../../../../../../doc/html/boostbook.css" type="text/css">
<meta name="generator" content="DocBook XSL Stylesheets V1.76.1"> <meta name="generator" content="DocBook XSL Stylesheets V1.66.1">
<link rel="home" href="../index.html" title="Chapter&#160;1.&#160;python 2.0"> <link rel="start" href="../index.html" title="Chapter 1. python 1.0">
<link rel="up" href="../index.html" title="Chapter&#160;1.&#160;python 2.0"> <link rel="up" href="../index.html" title="Chapter 1. python 1.0">
<link rel="prev" href="functions.html" title="Functions"> <link rel="prev" href="functions.html" title="Functions">
<link rel="next" href="embedding.html" title="Embedding"> <link rel="next" href="embedding.html" title="Embedding">
</head> </head>
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"> <body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
<table cellpadding="2" width="100%"><tr> <table cellpadding="2" width="100%"><tr>
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../../boost.png"></td> <td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../../boost.png"></td>
<td align="center"><a href="../../../../../../../index.html">Home</a></td> <td align="center"><a href="../../../../../../../index.htm">Home</a></td>
<td align="center"><a href="../../../../../../../libs/libraries.htm">Libraries</a></td> <td align="center"><a href="../../../../../../../libs/libraries.htm">Libraries</a></td>
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td> <td align="center"><a href="../../../../../../../people/people.htm">People</a></td>
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td> <td align="center"><a href="../../../../../../../more/faq.htm">FAQ</a></td>
<td align="center"><a href="../../../../../../../more/index.htm">More</a></td> <td align="center"><a href="../../../../../../../more/index.htm">More</a></td>
</tr></table> </tr></table>
<hr> <hr>
<div class="spirit-nav"> <div class="spirit-nav">
<a accesskey="p" href="functions.html"><img src="../../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="embedding.html"><img src="../../../../../../../doc/src/images/next.png" alt="Next"></a> <a accesskey="p" href="functions.html"><img src="../../../../../../../doc/html/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/html/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/html/images/home.png" alt="Home"></a><a accesskey="n" href="embedding.html"><img src="../../../../../../../doc/html/images/next.png" alt="Next"></a>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h2 class="title" style="clear: both"> <div class="titlepage"><div><div><h2 class="title" style="clear: both">
<a name="python.object"></a>Object Interface</h2></div></div></div> <a name="python.object"></a> Object Interface</h2></div></div></div>
<div class="toc"><dl> <div class="toc"><dl>
<dt><span class="section"><a href="object.html#python.basic_interface">Basic Interface</a></span></dt> <dt><span class="section"><a href="object.html#python.basic_interface">Basic Interface</a></span></dt>
<dt><span class="section"><a href="object.html#python.derived_object_types">Derived Object types</a></span></dt> <dt><span class="section"><a href="object.html#python.derived_object_types">Derived Object types</a></span></dt>
<dt><span class="section"><a href="object.html#python.extracting_c___objects">Extracting C++ objects</a></span></dt> <dt><span class="section"><a href="object.html#python.extracting_c___objects">Extracting C++ objects</a></span></dt>
<dt><span class="section"><a href="object.html#python.enums">Enums</a></span></dt> <dt><span class="section"><a href="object.html#python.enums">Enums</a></span></dt>
<dt><span class="section"><a href="object.html#python.creating_python_object">Creating <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">python</span><span class="special">::</span><span class="identifier">object</span></code> from <code class="computeroutput"><span class="identifier">PyObject</span><span class="special">*</span></code></a></span></dt>
</dl></div> </dl></div>
<p> <p>
Python is dynamically typed, unlike C++ which is statically typed. Python variables Python is dynamically typed, unlike C++ which is statically typed. Python variables
may hold an integer, a float, list, dict, tuple, str, long etc., among other may hold an integer, a float, list, dict, tuple, str, long etc., among other
things. In the viewpoint of Boost.Python and C++, these Pythonic variables things. In the viewpoint of Boost.Python and C++, these Pythonic variables
are just instances of class <code class="literal">object</code>. We will see in this are just instances of class <tt class="literal">object</tt>. We will see in this
chapter how to deal with Python objects. chapter how to deal with Python objects.
</p> </p>
<p> <p>
As mentioned, one of the goals of Boost.Python is to provide a bidirectional As mentioned, one of the goals of Boost.Python is to provide a bidirectional
mapping between C++ and Python while maintaining the Python feel. Boost.Python mapping between C++ and Python while maintaining the Python feel. Boost.Python
C++ <code class="literal">object</code>s are as close as possible to Python. This should C++ <tt class="literal">object</tt>s are as close as possible to Python. This should
minimize the learning curve significantly. minimize the learning curve significantly.
</p> </p>
<p> <p>
<span class="inlinemediaobject"><img src="../images/python.png" alt="python"></span> <span class="inlinemediaobject"><img src="../images/python.png" alt="python"></span>
</p> </p>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h3 class="title"> <div class="titlepage"><div><div><h3 class="title">
<a name="python.basic_interface"></a>Basic Interface</h3></div></div></div> <a name="python.basic_interface"></a>Basic Interface</h3></div></div></div>
<p> <p>
Class <code class="literal">object</code> wraps <code class="literal">PyObject*</code>. All the Class <tt class="literal">object</tt> wraps <tt class="literal">PyObject*</tt>. All the
intricacies of dealing with <code class="literal">PyObject</code>s such as managing intricacies of dealing with <tt class="literal">PyObject</tt>s such as managing
reference counting are handled by the <code class="literal">object</code> class. C++ reference counting are handled by the <tt class="literal">object</tt> class. C++
object interoperability is seamless. Boost.Python C++ <code class="literal">object</code>s object interoperability is seamless. Boost.Python C++ <tt class="literal">object</tt>s
can in fact be explicitly constructed from any C++ object. can in fact be explicitly constructed from any C++ object.
</p> </p>
<p> <p>
To illustrate, this Python code snippet: To illustrate, this Python code snippet:
</p> </p>
<pre class="programlisting"><span class="keyword">def</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">x</span><span class="special">,</span> <span class="identifier">y</span><span class="special">):</span> <p>
</p>
<pre class="programlisting">
<span class="keyword">def</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">x</span><span class="special">,</span> <span class="identifier">y</span><span class="special">):</span>
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">y</span> <span class="special">==</span> <span class="string">'foo'</span><span class="special">):</span> <span class="keyword">if</span> <span class="special">(</span><span class="identifier">y</span> <span class="special">==</span> <span class="string">'foo'</span><span class="special">):</span>
<span class="identifier">x</span><span class="special">[</span><span class="number">3</span><span class="special">:</span><span class="number">7</span><span class="special">]</span> <span class="special">=</span> <span class="string">'bar'</span> <span class="identifier">x</span><span class="special">[</span><span class="number">3</span><span class="special">:</span><span class="number">7</span><span class="special">]</span> <span class="special">=</span> <span class="string">'bar'</span>
<span class="keyword">else</span><span class="special">:</span> <span class="keyword">else</span><span class="special">:</span>
@@ -74,7 +76,10 @@
<p> <p>
Can be rewritten in C++ using Boost.Python facilities this way: Can be rewritten in C++ using Boost.Python facilities this way:
</p> </p>
<pre class="programlisting"><span class="identifier">object</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">object</span> <span class="identifier">x</span><span class="special">,</span> <span class="identifier">object</span> <span class="identifier">y</span><span class="special">)</span> <span class="special">{</span> <p>
</p>
<pre class="programlisting">
<span class="identifier">object</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">object</span> <span class="identifier">x</span><span class="special">,</span> <span class="identifier">object</span> <span class="identifier">y</span><span class="special">)</span> <span class="special">{</span>
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">y</span> <span class="special">==</span> <span class="string">"foo"</span><span class="special">)</span> <span class="keyword">if</span> <span class="special">(</span><span class="identifier">y</span> <span class="special">==</span> <span class="string">"foo"</span><span class="special">)</span>
<span class="identifier">x</span><span class="special">.</span><span class="identifier">slice</span><span class="special">(</span><span class="number">3</span><span class="special">,</span><span class="number">7</span><span class="special">)</span> <span class="special">=</span> <span class="string">"bar"</span><span class="special">;</span> <span class="identifier">x</span><span class="special">.</span><span class="identifier">slice</span><span class="special">(</span><span class="number">3</span><span class="special">,</span><span class="number">7</span><span class="special">)</span> <span class="special">=</span> <span class="string">"bar"</span><span class="special">;</span>
<span class="keyword">else</span> <span class="keyword">else</span>
@@ -90,114 +95,120 @@
in C++, the look and feel should be immediately apparent to the Python coder. in C++, the look and feel should be immediately apparent to the Python coder.
</p> </p>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h3 class="title"> <div class="titlepage"><div><div><h3 class="title">
<a name="python.derived_object_types"></a>Derived Object types</h3></div></div></div> <a name="python.derived_object_types"></a>Derived Object types</h3></div></div></div>
<p> <p>
Boost.Python comes with a set of derived <code class="literal">object</code> types Boost.Python comes with a set of derived <tt class="literal">object</tt> types
corresponding to that of Python's: corresponding to that of Python's:
</p> </p>
<div class="itemizedlist"><ul class="itemizedlist" type="disc"> <div class="itemizedlist"><ul type="disc">
<li class="listitem"> <li>
list list
</li> </li>
<li class="listitem"> <li>
dict dict
</li> </li>
<li class="listitem"> <li>
tuple tuple
</li> </li>
<li class="listitem"> <li>
str str
</li> </li>
<li class="listitem"> <li>
long_ long_
</li> </li>
<li class="listitem"> <li>
enum enum
</li> </li>
</ul></div> </ul></div>
<p> <p>
These derived <code class="literal">object</code> types act like real Python types. These derived <tt class="literal">object</tt> types act like real Python types.
For instance: For instance:
</p> </p>
<pre class="programlisting"><span class="identifier">str</span><span class="special">(</span><span class="number">1</span><span class="special">)</span> <span class="special">==&gt;</span> <span class="string">"1"</span> <pre class="programlisting">
<span class="identifier">str</span><span class="special">(</span><span class="number">1</span><span class="special">)</span> <span class="special">==&gt;</span> <span class="string">"1"</span>
</pre> </pre>
<p> <p>
Wherever appropriate, a particular derived <code class="literal">object</code> has Wherever appropriate, a particular derived <tt class="literal">object</tt> has
corresponding Python type's methods. For instance, <code class="literal">dict</code> corresponding Python type's methods. For instance, <tt class="literal">dict</tt>
has a <code class="literal">keys()</code> method: has a <tt class="literal">keys()</tt> method:
</p> </p>
<pre class="programlisting"><span class="identifier">d</span><span class="special">.</span><span class="identifier">keys</span><span class="special">()</span> <pre class="programlisting">
<span class="identifier">d</span><span class="special">.</span><span class="identifier">keys</span><span class="special">()</span>
</pre> </pre>
<p> <p>
<code class="literal">make_tuple</code> is provided for declaring <span class="emphasis"><em>tuple literals</em></span>. <tt class="literal">make_tuple</tt> is provided for declaring <span class="emphasis"><em>tuple literals</em></span>.
Example: Example:
</p> </p>
<pre class="programlisting"><span class="identifier">make_tuple</span><span class="special">(</span><span class="number">123</span><span class="special">,</span> <span class="char">'D'</span><span class="special">,</span> <span class="string">"Hello, World"</span><span class="special">,</span> <span class="number">0.0</span><span class="special">);</span> <pre class="programlisting">
<span class="identifier">make_tuple</span><span class="special">(</span><span class="number">123</span><span class="special">,</span> <span class="char">'D'</span><span class="special">,</span> <span class="string">"Hello, World"</span><span class="special">,</span> <span class="number">0.0</span><span class="special">);</span>
</pre> </pre>
<p> <p>
In C++, when Boost.Python <code class="literal">object</code>s are used as arguments In C++, when Boost.Python <tt class="literal">object</tt>s are used as arguments
to functions, subtype matching is required. For example, when a function to functions, subtype matching is required. For example, when a function
<code class="literal">f</code>, as declared below, is wrapped, it will only accept <tt class="literal">f</tt>, as declared below, is wrapped, it will only accept
instances of Python's <code class="literal">str</code> type and subtypes. instances of Python's <tt class="literal">str</tt> type and subtypes.
</p> </p>
<pre class="programlisting"><span class="keyword">void</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">str</span> <span class="identifier">name</span><span class="special">)</span> <pre class="programlisting">
<span class="keyword">void</span> <span class="identifier">f</span><span class="special">(</span><span class="identifier">str</span> <span class="identifier">name</span><span class="special">)</span>
<span class="special">{</span> <span class="special">{</span>
<span class="identifier">object</span> <span class="identifier">n2</span> <span class="special">=</span> <span class="identifier">name</span><span class="special">.</span><span class="identifier">attr</span><span class="special">(</span><span class="string">"upper"</span><span class="special">)();</span> <span class="comment">// NAME = name.upper()</span> <span class="identifier">object</span> <span class="identifier">n2</span> <span class="special">=</span> <span class="identifier">name</span><span class="special">.</span><span class="identifier">attr</span><span class="special">(</span><span class="string">"upper"</span><span class="special">)();</span> <span class="comment">// NAME = name.upper()
<span class="identifier">str</span> <span class="identifier">NAME</span> <span class="special">=</span> <span class="identifier">name</span><span class="special">.</span><span class="identifier">upper</span><span class="special">();</span> <span class="comment">// better</span> </span> <span class="identifier">str</span> <span class="identifier">NAME</span> <span class="special">=</span> <span class="identifier">name</span><span class="special">.</span><span class="identifier">upper</span><span class="special">();</span> <span class="comment">// better
<span class="identifier">object</span> <span class="identifier">msg</span> <span class="special">=</span> <span class="string">"%s is bigger than %s"</span> <span class="special">%</span> <span class="identifier">make_tuple</span><span class="special">(</span><span class="identifier">NAME</span><span class="special">,</span><span class="identifier">name</span><span class="special">);</span> </span> <span class="identifier">object</span> <span class="identifier">msg</span> <span class="special">=</span> <span class="string">"%s is bigger than %s"</span> <span class="special">%</span> <span class="identifier">make_tuple</span><span class="special">(</span><span class="identifier">NAME</span><span class="special">,</span><span class="identifier">name</span><span class="special">);</span>
<span class="special">}</span> <span class="special">}</span>
</pre> </pre>
<p> <p>
In finer detail: In finer detail:
</p> </p>
<pre class="programlisting"><span class="identifier">str</span> <span class="identifier">NAME</span> <span class="special">=</span> <span class="identifier">name</span><span class="special">.</span><span class="identifier">upper</span><span class="special">();</span> <pre class="programlisting">
<span class="identifier">str</span> <span class="identifier">NAME</span> <span class="special">=</span> <span class="identifier">name</span><span class="special">.</span><span class="identifier">upper</span><span class="special">();</span>
</pre> </pre>
<p> <p>
Illustrates that we provide versions of the str type's methods as C++ member Illustrates that we provide versions of the str type's methods as C++ member
functions. functions.
</p> </p>
<pre class="programlisting"><span class="identifier">object</span> <span class="identifier">msg</span> <span class="special">=</span> <span class="string">"%s is bigger than %s"</span> <span class="special">%</span> <span class="identifier">make_tuple</span><span class="special">(</span><span class="identifier">NAME</span><span class="special">,</span><span class="identifier">name</span><span class="special">);</span> <pre class="programlisting">
<span class="identifier">object</span> <span class="identifier">msg</span> <span class="special">=</span> <span class="string">"%s is bigger than %s"</span> <span class="special">%</span> <span class="identifier">make_tuple</span><span class="special">(</span><span class="identifier">NAME</span><span class="special">,</span><span class="identifier">name</span><span class="special">);</span>
</pre> </pre>
<p> <p>
Demonstrates that you can write the C++ equivalent of <code class="literal">"format" Demonstrates that you can write the C++ equivalent of <tt class="literal">"format"
% x,y,z</code> in Python, which is useful since there's no easy way to % x,y,z</tt> in Python, which is useful since there's no easy way to
do that in std C++. do that in std C++.
</p> </p>
<div class="sidebar"> <div class="sidebar"><p>
<div class="titlepage"></div> <span class="inlinemediaobject"><img src="../images/alert.png" alt="alert"></span> <span class="bold"><b>Beware</b></span> the common pitfall
<p>
<span class="inlinemediaobject"><img src="../images/alert.png" alt="alert"></span> <span class="bold"><strong>Beware</strong></span> the common pitfall
of forgetting that the constructors of most of Python's mutable types make of forgetting that the constructors of most of Python's mutable types make
copies, just as in Python. copies, just as in Python.
</p> </p></div>
</div>
<p> <p>
Python: Python:
</p> </p>
<pre class="programlisting"><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="comment"># copies x.__dict__</span> <pre class="programlisting">
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">d</span><span class="special">[</span><span class="string">'whatever'</span><span class="special">]</span> <span class="special">=</span> <span class="number">3</span> <span class="comment"># modifies the copy</span> <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="comment"># copies x.__dict__
</pre> </span><span class="special">&gt;&gt;&gt;</span> <span class="identifier">d</span><span class="special">[</span><span class="string">'whatever'</span><span class="special">]</span> <span class="special">=</span> <span class="number">3</span> <span class="comment"># modifies the copy
</span></pre>
<p> <p>
C++: C++:
</p> </p>
<pre class="programlisting"><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">"__dict__"</span><span class="special">));</span> <span class="comment">// copies x.__dict__</span> <pre class="programlisting">
<span class="identifier">d</span><span class="special">[</span><span class="char">'whatever'</span><span class="special">]</span> <span class="special">=</span> <span class="number">3</span><span class="special">;</span> <span class="comment">// modifies the copy</span> <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">"__dict__"</span><span class="special">));</span> <span class="comment">// copies x.__dict__
</pre> </span><span class="identifier">d</span><span class="special">[</span><span class="char">'whatever'</span><span class="special">]</span> <span class="special">=</span> <span class="number">3</span><span class="special">;</span> <span class="comment">// modifies the copy
<h3> </span></pre>
<a name="derived_object_types.class__lt_t_gt__as_objects"></a> <a name="derived_object_types.class__lt_t_gt__as_objects"></a><h2>
<a name="id469586"></a>
class_&lt;T&gt; as objects class_&lt;T&gt; as objects
</h3> </h2>
<p> <p>
Due to the dynamic nature of Boost.Python objects, any <code class="literal">class_&lt;T&gt;</code> Due to the dynamic nature of Boost.Python objects, any <tt class="literal">class_&lt;T&gt;</tt>
may also be one of these types! The following code snippet wraps the class may also be one of these types! The following code snippet wraps the class
(type) object. (type) object.
</p> </p>
<p> <p>
We can use this to create wrapped instances. Example: We can use this to create wrapped instances. Example:
</p> </p>
<pre class="programlisting"><span class="identifier">object</span> <span class="identifier">vec345</span> <span class="special">=</span> <span class="special">(</span> <pre class="programlisting">
<span class="identifier">object</span> <span class="identifier">vec345</span> <span class="special">=</span> <span class="special">(</span>
<span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">Vec2</span><span class="special">&gt;(</span><span class="string">"Vec2"</span><span class="special">,</span> <span class="identifier">init</span><span class="special">&lt;</span><span class="keyword">double</span><span class="special">,</span> <span class="keyword">double</span><span class="special">&gt;())</span> <span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">Vec2</span><span class="special">&gt;(</span><span class="string">"Vec2"</span><span class="special">,</span> <span class="identifier">init</span><span class="special">&lt;</span><span class="keyword">double</span><span class="special">,</span> <span class="keyword">double</span><span class="special">&gt;())</span>
<span class="special">.</span><span class="identifier">def_readonly</span><span class="special">(</span><span class="string">"length"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">Point</span><span class="special">::</span><span class="identifier">length</span><span class="special">)</span> <span class="special">.</span><span class="identifier">def_readonly</span><span class="special">(</span><span class="string">"length"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">Point</span><span class="special">::</span><span class="identifier">length</span><span class="special">)</span>
<span class="special">.</span><span class="identifier">def_readonly</span><span class="special">(</span><span class="string">"angle"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">Point</span><span class="special">::</span><span class="identifier">angle</span><span class="special">)</span> <span class="special">.</span><span class="identifier">def_readonly</span><span class="special">(</span><span class="string">"angle"</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">Point</span><span class="special">::</span><span class="identifier">angle</span><span class="special">)</span>
@@ -206,85 +217,91 @@
<span class="identifier">assert</span><span class="special">(</span><span class="identifier">vec345</span><span class="special">.</span><span class="identifier">attr</span><span class="special">(</span><span class="string">"length"</span><span class="special">)</span> <span class="special">==</span> <span class="number">5.0</span><span class="special">);</span> <span class="identifier">assert</span><span class="special">(</span><span class="identifier">vec345</span><span class="special">.</span><span class="identifier">attr</span><span class="special">(</span><span class="string">"length"</span><span class="special">)</span> <span class="special">==</span> <span class="number">5.0</span><span class="special">);</span>
</pre> </pre>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h3 class="title"> <div class="titlepage"><div><div><h3 class="title">
<a name="python.extracting_c___objects"></a>Extracting C++ objects</h3></div></div></div> <a name="python.extracting_c___objects"></a>Extracting C++ objects</h3></div></div></div>
<p> <p>
At some point, we will need to get C++ values out of object instances. This At some point, we will need to get C++ values out of object instances. This
can be achieved with the <code class="literal">extract&lt;T&gt;</code> function. Consider can be achieved with the <tt class="literal">extract&lt;T&gt;</tt> function. Consider
the following: the following:
</p> </p>
<pre class="programlisting"><span class="keyword">double</span> <span class="identifier">x</span> <span class="special">=</span> <span class="identifier">o</span><span class="special">.</span><span class="identifier">attr</span><span class="special">(</span><span class="string">"length"</span><span class="special">);</span> <span class="comment">// compile error</span> <pre class="programlisting">
</pre> <span class="keyword">double</span> <span class="identifier">x</span> <span class="special">=</span> <span class="identifier">o</span><span class="special">.</span><span class="identifier">attr</span><span class="special">(</span><span class="string">"length"</span><span class="special">);</span> <span class="comment">// compile error
</span></pre>
<p> <p>
In the code above, we got a compiler error because Boost.Python <code class="literal">object</code> In the code above, we got a compiler error because Boost.Python <tt class="literal">object</tt>
can't be implicitly converted to <code class="literal">double</code>s. Instead, what can't be implicitly converted to <tt class="literal">double</tt>s. Instead, what
we wanted to do above can be achieved by writing: we wanted to do above can be achieved by writing:
</p> </p>
<pre class="programlisting"><span class="keyword">double</span> <span class="identifier">l</span> <span class="special">=</span> <span class="identifier">extract</span><span class="special">&lt;</span><span class="keyword">double</span><span class="special">&gt;(</span><span class="identifier">o</span><span class="special">.</span><span class="identifier">attr</span><span class="special">(</span><span class="string">"length"</span><span class="special">));</span> <pre class="programlisting">
<span class="keyword">double</span> <span class="identifier">l</span> <span class="special">=</span> <span class="identifier">extract</span><span class="special">&lt;</span><span class="keyword">double</span><span class="special">&gt;(</span><span class="identifier">o</span><span class="special">.</span><span class="identifier">attr</span><span class="special">(</span><span class="string">"length"</span><span class="special">));</span>
<span class="identifier">Vec2</span><span class="special">&amp;</span> <span class="identifier">v</span> <span class="special">=</span> <span class="identifier">extract</span><span class="special">&lt;</span><span class="identifier">Vec2</span><span class="special">&amp;&gt;(</span><span class="identifier">o</span><span class="special">);</span> <span class="identifier">Vec2</span><span class="special">&amp;</span> <span class="identifier">v</span> <span class="special">=</span> <span class="identifier">extract</span><span class="special">&lt;</span><span class="identifier">Vec2</span><span class="special">&amp;&gt;(</span><span class="identifier">o</span><span class="special">);</span>
<span class="identifier">assert</span><span class="special">(</span><span class="identifier">l</span> <span class="special">==</span> <span class="identifier">v</span><span class="special">.</span><span class="identifier">length</span><span class="special">());</span> <span class="identifier">assert</span><span class="special">(</span><span class="identifier">l</span> <span class="special">==</span> <span class="identifier">v</span><span class="special">.</span><span class="identifier">length</span><span class="special">());</span>
</pre> </pre>
<p> <p>
The first line attempts to extract the "length" attribute of the The first line attempts to extract the "length" attribute of the
Boost.Python <code class="literal">object</code>. The second line attempts to <span class="emphasis"><em>extract</em></span> Boost.Python <tt class="literal">object</tt>. The second line attempts to <span class="emphasis"><em>extract</em></span>
the <code class="literal">Vec2</code> object from held by the Boost.Python <code class="literal">object</code>. the <tt class="literal">Vec2</tt> object from held by the Boost.Python <tt class="literal">object</tt>.
</p> </p>
<p> <p>
Take note that we said "attempt to" above. What if the Boost.Python Take note that we said "attempt to" above. What if the Boost.Python
<code class="literal">object</code> does not really hold a <code class="literal">Vec2</code> <tt class="literal">object</tt> does not really hold a <tt class="literal">Vec2</tt>
type? This is certainly a possibility considering the dynamic nature of Python type? This is certainly a possibility considering the dynamic nature of Python
<code class="literal">object</code>s. To be on the safe side, if the C++ type can't <tt class="literal">object</tt>s. To be on the safe side, if the C++ type can't
be extracted, an appropriate exception is thrown. To avoid an exception, be extracted, an appropriate exception is thrown. To avoid an exception,
we need to test for extractibility: we need to test for extractibility:
</p> </p>
<pre class="programlisting"><span class="identifier">extract</span><span class="special">&lt;</span><span class="identifier">Vec2</span><span class="special">&amp;&gt;</span> <span class="identifier">x</span><span class="special">(</span><span class="identifier">o</span><span class="special">);</span> <pre class="programlisting">
<span class="identifier">extract</span><span class="special">&lt;</span><span class="identifier">Vec2</span><span class="special">&amp;&gt;</span> <span class="identifier">x</span><span class="special">(</span><span class="identifier">o</span><span class="special">);</span>
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">x</span><span class="special">.</span><span class="identifier">check</span><span class="special">())</span> <span class="special">{</span> <span class="keyword">if</span> <span class="special">(</span><span class="identifier">x</span><span class="special">.</span><span class="identifier">check</span><span class="special">())</span> <span class="special">{</span>
<span class="identifier">Vec2</span><span class="special">&amp;</span> <span class="identifier">v</span> <span class="special">=</span> <span class="identifier">x</span><span class="special">();</span> <span class="special">...</span> <span class="identifier">Vec2</span><span class="special">&amp;</span> <span class="identifier">v</span> <span class="special">=</span> <span class="identifier">x</span><span class="special">();</span> <span class="special">...</span>
</pre> </pre>
<p> <p>
<span class="inlinemediaobject"><img src="../images/tip.png" alt="tip"></span> The astute reader might have noticed that the <code class="literal">extract&lt;T&gt;</code> <span class="inlinemediaobject"><img src="../images/tip.png" alt="tip"></span> The astute reader might have noticed that the <tt class="literal">extract&lt;T&gt;</tt>
facility in fact solves the mutable copying problem: facility in fact solves the mutable copying problem:
</p> </p>
<pre class="programlisting"><span class="identifier">dict</span> <span class="identifier">d</span> <span class="special">=</span> <span class="identifier">extract</span><span class="special">&lt;</span><span class="identifier">dict</span><span class="special">&gt;(</span><span class="identifier">x</span><span class="special">.</span><span class="identifier">attr</span><span class="special">(</span><span class="string">"__dict__"</span><span class="special">));</span> <pre class="programlisting">
<span class="identifier">d</span><span class="special">[</span><span class="string">"whatever"</span><span class="special">]</span> <span class="special">=</span> <span class="number">3</span><span class="special">;</span> <span class="comment">// modifies x.__dict__ !</span> <span class="identifier">dict</span> <span class="identifier">d</span> <span class="special">=</span> <span class="identifier">extract</span><span class="special">&lt;</span><span class="identifier">dict</span><span class="special">&gt;(</span><span class="identifier">x</span><span class="special">.</span><span class="identifier">attr</span><span class="special">(</span><span class="string">"__dict__"</span><span class="special">));</span>
</pre> <span class="identifier">d</span><span class="special">[</span><span class="string">"whatever"</span><span class="special">]</span> <span class="special">=</span> <span class="number">3</span><span class="special">;</span> <span class="comment">// modifies x.__dict__ !
</span></pre>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h3 class="title"> <div class="titlepage"><div><div><h3 class="title">
<a name="python.enums"></a>Enums</h3></div></div></div> <a name="python.enums"></a>Enums</h3></div></div></div>
<p> <p>
Boost.Python has a nifty facility to capture and wrap C++ enums. While Python Boost.Python has a nifty facility to capture and wrap C++ enums. While Python
has no <code class="literal">enum</code> type, we'll often want to expose our C++ enums has no <tt class="literal">enum</tt> type, we'll often want to expose our C++ enums
to Python as an <code class="literal">int</code>. Boost.Python's enum facility makes to Python as an <tt class="literal">int</tt>. Boost.Python's enum facility makes
this easy while taking care of the proper conversions from Python's dynamic this easy while taking care of the proper conversions from Python's dynamic
typing to C++'s strong static typing (in C++, ints cannot be implicitly converted typing to C++'s strong static typing (in C++, ints cannot be implicitly converted
to enums). To illustrate, given a C++ enum: to enums). To illustrate, given a C++ enum:
</p> </p>
<pre class="programlisting"><span class="keyword">enum</span> <span class="identifier">choice</span> <span class="special">{</span> <span class="identifier">red</span><span class="special">,</span> <span class="identifier">blue</span> <span class="special">};</span> <pre class="programlisting">
<span class="keyword">enum</span> <span class="identifier">choice</span> <span class="special">{</span> <span class="identifier">red</span><span class="special">,</span> <span class="identifier">blue</span> <span class="special">};</span>
</pre> </pre>
<p> <p>
the construct: the construct:
</p> </p>
<pre class="programlisting"><span class="identifier">enum_</span><span class="special">&lt;</span><span class="identifier">choice</span><span class="special">&gt;(</span><span class="string">"choice"</span><span class="special">)</span> <pre class="programlisting">
<span class="identifier">enum_</span><span class="special">&lt;</span><span class="identifier">choice</span><span class="special">&gt;(</span><span class="string">"choice"</span><span class="special">)</span>
<span class="special">.</span><span class="identifier">value</span><span class="special">(</span><span class="string">"red"</span><span class="special">,</span> <span class="identifier">red</span><span class="special">)</span> <span class="special">.</span><span class="identifier">value</span><span class="special">(</span><span class="string">"red"</span><span class="special">,</span> <span class="identifier">red</span><span class="special">)</span>
<span class="special">.</span><span class="identifier">value</span><span class="special">(</span><span class="string">"blue"</span><span class="special">,</span> <span class="identifier">blue</span><span class="special">)</span> <span class="special">.</span><span class="identifier">value</span><span class="special">(</span><span class="string">"blue"</span><span class="special">,</span> <span class="identifier">blue</span><span class="special">)</span>
<span class="special">;</span> <span class="special">;</span>
</pre> </pre>
<p> <p>
can be used to expose to Python. The new enum type is created in the current can be used to expose to Python. The new enum type is created in the current
<code class="literal">scope()</code>, which is usually the current module. The snippet <tt class="literal">scope()</tt>, which is usually the current module. The snippet
above creates a Python class derived from Python's <code class="literal">int</code> above creates a Python class derived from Python's <tt class="literal">int</tt>
type which is associated with the C++ type passed as its first parameter. type which is associated with the C++ type passed as its first parameter.
</p> </p>
<div class="note"><table border="0" summary="Note"> <div class="note"><table border="0" summary="Note">
<tr> <tr>
<td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../../../doc/src/images/note.png"></td> <td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../../../doc/html/images/note.png"></td>
<th align="left">Note</th> <th align="left">Note</th>
</tr> </tr>
<tr><td align="left" valign="top"> <tr><td colspan="2" align="left" valign="top">
<p> <p>
<span class="bold"><strong>what is a scope?</strong></span> <span class="bold"><b>what is a scope?</b></span>
</p> </p>
<p> <p>
The scope is a class that has an associated global Python object which The scope is a class that has an associated global Python object which
@@ -296,55 +313,35 @@
<p> <p>
You can access those values in Python as You can access those values in Python as
</p> </p>
<pre class="programlisting"><span class="special">&gt;&gt;&gt;</span> <span class="identifier">my_module</span><span class="special">.</span><span class="identifier">choice</span><span class="special">.</span><span class="identifier">red</span> <p>
</p>
<pre class="programlisting">
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">my_module</span><span class="special">.</span><span class="identifier">choice</span><span class="special">.</span><span class="identifier">red</span>
<span class="identifier">my_module</span><span class="special">.</span><span class="identifier">choice</span><span class="special">.</span><span class="identifier">red</span> <span class="identifier">my_module</span><span class="special">.</span><span class="identifier">choice</span><span class="special">.</span><span class="identifier">red</span>
</pre> </pre>
<p> <p>
where my_module is the module where the enum is declared. You can also create where my_module is the module where the enum is declared. You can also create
a new scope around a class: a new scope around a class:
</p> </p>
<pre class="programlisting"><span class="identifier">scope</span> <span class="identifier">in_X</span> <span class="special">=</span> <span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">X</span><span class="special">&gt;(</span><span class="string">"X"</span><span class="special">)</span> <p>
</p>
<pre class="programlisting">
<span class="identifier">scope</span> <span class="identifier">in_X</span> <span class="special">=</span> <span class="identifier">class_</span><span class="special">&lt;</span><span class="identifier">X</span><span class="special">&gt;(</span><span class="string">"X"</span><span class="special">)</span>
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span> <span class="special">...</span> <span class="special">)</span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span> <span class="special">...</span> <span class="special">)</span>
<span class="special">.</span><span class="identifier">def</span><span class="special">(</span> <span class="special">...</span> <span class="special">)</span> <span class="special">.</span><span class="identifier">def</span><span class="special">(</span> <span class="special">...</span> <span class="special">)</span>
<span class="special">;</span> <span class="special">;</span>
<span class="comment">// Expose X::nested as X.nested</span> <span class="comment">// Expose X::nested as X.nested
<span class="identifier">enum_</span><span class="special">&lt;</span><span class="identifier">X</span><span class="special">::</span><span class="identifier">nested</span><span class="special">&gt;(</span><span class="string">"nested"</span><span class="special">)</span> </span><span class="identifier">enum_</span><span class="special">&lt;</span><span class="identifier">X</span><span class="special">::</span><span class="identifier">nested</span><span class="special">&gt;(</span><span class="string">"nested"</span><span class="special">)</span>
<span class="special">.</span><span class="identifier">value</span><span class="special">(</span><span class="string">"red"</span><span class="special">,</span> <span class="identifier">red</span><span class="special">)</span> <span class="special">.</span><span class="identifier">value</span><span class="special">(</span><span class="string">"red"</span><span class="special">,</span> <span class="identifier">red</span><span class="special">)</span>
<span class="special">.</span><span class="identifier">value</span><span class="special">(</span><span class="string">"blue"</span><span class="special">,</span> <span class="identifier">blue</span><span class="special">)</span> <span class="special">.</span><span class="identifier">value</span><span class="special">(</span><span class="string">"blue"</span><span class="special">,</span> <span class="identifier">blue</span><span class="special">)</span>
<span class="special">;</span> <span class="special">;</span>
</pre> </pre>
</div> </div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="python.creating_python_object"></a>Creating <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">python</span><span class="special">::</span><span class="identifier">object</span></code> from <code class="computeroutput"><span class="identifier">PyObject</span><span class="special">*</span></code>
</h3></div></div></div>
<p>
When you want a <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">python</span><span class="special">::</span><span class="identifier">object</span></code> to manage a pointer to <code class="computeroutput"><span class="identifier">PyObject</span><span class="special">*</span></code>
pyobj one does:
</p>
<pre class="programlisting"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">python</span><span class="special">::</span><span class="identifier">object</span> <span class="identifier">o</span><span class="special">(</span><span class="identifier">boost</span><span class="special">::</span><span class="identifier">python</span><span class="special">::</span><span class="identifier">handle</span><span class="special">&lt;&gt;(</span><span class="identifier">pyobj</span><span class="special">));</span>
</pre>
<p>
In this case, the <code class="computeroutput"><span class="identifier">o</span></code> object,
manages the <code class="computeroutput"><span class="identifier">pyobj</span></code>, it won&#8217;t
increase the reference count on construction.
</p>
<p>
Otherwise, to use a borrowed reference:
</p>
<pre class="programlisting"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">python</span><span class="special">::</span><span class="identifier">object</span> <span class="identifier">o</span><span class="special">(</span><span class="identifier">boost</span><span class="special">::</span><span class="identifier">python</span><span class="special">::</span><span class="identifier">handle</span><span class="special">&lt;&gt;(</span><span class="identifier">boost</span><span class="special">::</span><span class="identifier">python</span><span class="special">::</span><span class="identifier">borrowed</span><span class="special">(</span><span class="identifier">pyobj</span><span class="special">)));</span>
</pre>
<p>
In this case, <code class="computeroutput"><span class="identifier">Py_INCREF</span></code> is
called, so <code class="computeroutput"><span class="identifier">pyobj</span></code> is not destructed
when object o goes out of scope.
</p>
</div>
</div> </div>
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr> <table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
<td align="left"></td> <td align="left"></td>
<td align="right"><div class="copyright-footer">Copyright &#169; 2002-2005 Joel <td align="right"><div class="copyright-footer">Copyright © 2002-2005 Joel
de Guzman, David Abrahams<p> de Guzman, David Abrahams<p>
Distributed under the Boost Software License, Version 1.0. (See accompanying Distributed under the Boost Software License, Version 1.0. (See accompanying
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top"> file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">
@@ -354,7 +351,7 @@
</tr></table> </tr></table>
<hr> <hr>
<div class="spirit-nav"> <div class="spirit-nav">
<a accesskey="p" href="functions.html"><img src="../../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="embedding.html"><img src="../../../../../../../doc/src/images/next.png" alt="Next"></a> <a accesskey="p" href="functions.html"><img src="../../../../../../../doc/html/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/html/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/html/images/home.png" alt="Home"></a><a accesskey="n" href="embedding.html"><img src="../../../../../../../doc/html/images/next.png" alt="Next"></a>
</div> </div>
</body> </body>
</html> </html>

View File

@@ -1,29 +1,29 @@
<html> <html>
<head> <head>
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII"> <meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
<title>General Techniques</title> <title> General Techniques</title>
<link rel="stylesheet" href="../../../../../../../doc/src/boostbook.css" type="text/css"> <link rel="stylesheet" href="../../../../../../../doc/html/boostbook.css" type="text/css">
<meta name="generator" content="DocBook XSL Stylesheets V1.76.1"> <meta name="generator" content="DocBook XSL Stylesheets V1.66.1">
<link rel="home" href="../index.html" title="Chapter&#160;1.&#160;python 2.0"> <link rel="start" href="../index.html" title="Chapter 1. python 1.0">
<link rel="up" href="../index.html" title="Chapter&#160;1.&#160;python 2.0"> <link rel="up" href="../index.html" title="Chapter 1. python 1.0">
<link rel="prev" href="exception.html" title="Exception Translation"> <link rel="prev" href="exception.html" title=" Exception Translation">
</head> </head>
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"> <body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
<table cellpadding="2" width="100%"><tr> <table cellpadding="2" width="100%"><tr>
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../../boost.png"></td> <td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../../boost.png"></td>
<td align="center"><a href="../../../../../../../index.html">Home</a></td> <td align="center"><a href="../../../../../../../index.htm">Home</a></td>
<td align="center"><a href="../../../../../../../libs/libraries.htm">Libraries</a></td> <td align="center"><a href="../../../../../../../libs/libraries.htm">Libraries</a></td>
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td> <td align="center"><a href="../../../../../../../people/people.htm">People</a></td>
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td> <td align="center"><a href="../../../../../../../more/faq.htm">FAQ</a></td>
<td align="center"><a href="../../../../../../../more/index.htm">More</a></td> <td align="center"><a href="../../../../../../../more/index.htm">More</a></td>
</tr></table> </tr></table>
<hr> <hr>
<div class="spirit-nav"> <div class="spirit-nav">
<a accesskey="p" href="exception.html"><img src="../../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/src/images/home.png" alt="Home"></a> <a accesskey="p" href="exception.html"><img src="../../../../../../../doc/html/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/html/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/html/images/home.png" alt="Home"></a>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h2 class="title" style="clear: both"> <div class="titlepage"><div><div><h2 class="title" style="clear: both">
<a name="python.techniques"></a>General Techniques</h2></div></div></div> <a name="python.techniques"></a> General Techniques</h2></div></div></div>
<div class="toc"><dl> <div class="toc"><dl>
<dt><span class="section"><a href="techniques.html#python.creating_packages">Creating Packages</a></span></dt> <dt><span class="section"><a href="techniques.html#python.creating_packages">Creating Packages</a></span></dt>
<dt><span class="section"><a href="techniques.html#python.extending_wrapped_objects_in_python">Extending Wrapped Objects in Python</a></span></dt> <dt><span class="section"><a href="techniques.html#python.extending_wrapped_objects_in_python">Extending Wrapped Objects in Python</a></span></dt>
@@ -33,7 +33,7 @@
Here are presented some useful techniques that you can use while wrapping code Here are presented some useful techniques that you can use while wrapping code
with Boost.Python. with Boost.Python.
</p> </p>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h3 class="title"> <div class="titlepage"><div><div><h3 class="title">
<a name="python.creating_packages"></a>Creating Packages</h3></div></div></div> <a name="python.creating_packages"></a>Creating Packages</h3></div></div></div>
<p> <p>
@@ -50,10 +50,11 @@
<p> <p>
We have a C++ library that works with sounds: reading and writing various We have a C++ library that works with sounds: reading and writing various
formats, applying filters to the sound data, etc. It is named (conveniently) formats, applying filters to the sound data, etc. It is named (conveniently)
<code class="literal">sounds</code>. Our library already has a neat C++ namespace hierarchy, <tt class="literal">sounds</tt>. Our library already has a neat C++ namespace hierarchy,
like so: like so:
</p> </p>
<pre class="programlisting"><span class="identifier">sounds</span><span class="special">::</span><span class="identifier">core</span> <pre class="programlisting">
<span class="identifier">sounds</span><span class="special">::</span><span class="identifier">core</span>
<span class="identifier">sounds</span><span class="special">::</span><span class="identifier">io</span> <span class="identifier">sounds</span><span class="special">::</span><span class="identifier">io</span>
<span class="identifier">sounds</span><span class="special">::</span><span class="identifier">filters</span> <span class="identifier">sounds</span><span class="special">::</span><span class="identifier">filters</span>
</pre> </pre>
@@ -61,14 +62,16 @@
We would like to present this same hierarchy to the Python user, allowing We would like to present this same hierarchy to the Python user, allowing
him to write code like this: him to write code like this:
</p> </p>
<pre class="programlisting"><span class="keyword">import</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">filters</span> <pre class="programlisting">
<span class="identifier">sounds</span><span class="special">.</span><span class="identifier">filters</span><span class="special">.</span><span class="identifier">echo</span><span class="special">(...)</span> <span class="comment"># echo is a C++ function</span> <span class="keyword">import</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">filters</span>
</pre> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">filters</span><span class="special">.</span><span class="identifier">echo</span><span class="special">(...)</span> <span class="comment"># echo is a C++ function
</span></pre>
<p> <p>
The first step is to write the wrapping code. We have to export each module The first step is to write the wrapping code. We have to export each module
separately with Boost.Python, like this: separately with Boost.Python, like this:
</p> </p>
<pre class="programlisting"><span class="special">/*</span> <span class="identifier">file</span> <span class="identifier">core</span><span class="special">.</span><span class="identifier">cpp</span> <span class="special">*/</span> <pre class="programlisting">
<span class="special">/*</span> <span class="identifier">file</span> <span class="identifier">core</span><span class="special">.</span><span class="identifier">cpp</span> <span class="special">*/</span>
<span class="identifier">BOOST_PYTHON_MODULE</span><span class="special">(</span><span class="identifier">core</span><span class="special">)</span> <span class="identifier">BOOST_PYTHON_MODULE</span><span class="special">(</span><span class="identifier">core</span><span class="special">)</span>
<span class="special">{</span> <span class="special">{</span>
<span class="special">/*</span> <span class="identifier">export</span> <span class="identifier">everything</span> <span class="keyword">in</span> <span class="identifier">the</span> <span class="identifier">sounds</span><span class="special">::</span><span class="identifier">core</span> <span class="identifier">namespace</span> <span class="special">*/</span> <span class="special">/*</span> <span class="identifier">export</span> <span class="identifier">everything</span> <span class="keyword">in</span> <span class="identifier">the</span> <span class="identifier">sounds</span><span class="special">::</span><span class="identifier">core</span> <span class="identifier">namespace</span> <span class="special">*/</span>
@@ -90,18 +93,18 @@
<span class="special">}</span> <span class="special">}</span>
</pre> </pre>
<p> <p>
Compiling these files will generate the following Python extensions: <code class="literal">core.pyd</code>, Compiling these files will generate the following Python extensions: <tt class="literal">core.pyd</tt>,
<code class="literal">io.pyd</code> and <code class="literal">filters.pyd</code>. <tt class="literal">io.pyd</tt> and <tt class="literal">filters.pyd</tt>.
</p> </p>
<div class="note"><table border="0" summary="Note"> <div class="note"><table border="0" summary="Note">
<tr> <tr>
<td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../../../doc/src/images/note.png"></td> <td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../../../doc/html/images/note.png"></td>
<th align="left">Note</th> <th align="left">Note</th>
</tr> </tr>
<tr><td align="left" valign="top"><p> <tr><td colspan="2" align="left" valign="top"><p>
The extension <code class="literal">.pyd</code> is used for python extension modules, The extension <tt class="literal">.pyd</tt> is used for python extension modules,
which are just shared libraries. Using the default for your system, like which are just shared libraries. Using the default for your system, like
<code class="literal">.so</code> for Unix and <code class="literal">.dll</code> for Windows, <tt class="literal">.so</tt> for Unix and <tt class="literal">.dll</tt> for Windows,
works just as well. works just as well.
</p></td></tr> </p></td></tr>
</table></div> </table></div>
@@ -115,16 +118,19 @@
io.pyd io.pyd
</pre> </pre>
<p> <p>
The file <code class="literal">__init__.py</code> is what tells Python that the directory The file <tt class="literal">__init__.py</tt> is what tells Python that the directory
<code class="literal">sounds/</code> is actually a Python package. It can be a empty <tt class="literal">sounds/</tt> is actually a Python package. It can be a empty
file, but can also perform some magic, that will be shown later. file, but can also perform some magic, that will be shown later.
</p> </p>
<p> <p>
Now our package is ready. All the user has to do is put <code class="literal">sounds</code> Now our package is ready. All the user has to do is put <tt class="literal">sounds</tt>
into his <a href="http://www.python.org/doc/current/tut/node8.html#SECTION008110000000000000000" target="_top">PYTHONPATH</a> into his <a href="http://www.python.org/doc/current/tut/node8.html#SECTION008110000000000000000" target="_top">PYTHONPATH</a>
and fire up the interpreter: and fire up the interpreter:
</p> </p>
<pre class="programlisting"><span class="special">&gt;&gt;&gt;</span> <span class="keyword">import</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">io</span> <p>
</p>
<pre class="programlisting">
<span class="special">&gt;&gt;&gt;</span> <span class="keyword">import</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">io</span>
<span class="special">&gt;&gt;&gt;</span> <span class="keyword">import</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">filters</span> <span class="special">&gt;&gt;&gt;</span> <span class="keyword">import</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">filters</span>
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">sound</span> <span class="special">=</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">io</span><span class="special">.</span><span class="identifier">open</span><span class="special">(</span><span class="string">'file.mp3'</span><span class="special">)</span> <span class="special">&gt;&gt;&gt;</span> <span class="identifier">sound</span> <span class="special">=</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">io</span><span class="special">.</span><span class="identifier">open</span><span class="special">(</span><span class="string">'file.mp3'</span><span class="special">)</span>
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">new_sound</span> <span class="special">=</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">filters</span><span class="special">.</span><span class="identifier">echo</span><span class="special">(</span><span class="identifier">sound</span><span class="special">,</span> <span class="number">1.0</span><span class="special">)</span> <span class="special">&gt;&gt;&gt;</span> <span class="identifier">new_sound</span> <span class="special">=</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">filters</span><span class="special">.</span><span class="identifier">echo</span><span class="special">(</span><span class="identifier">sound</span><span class="special">,</span> <span class="number">1.0</span><span class="special">)</span>
@@ -144,7 +150,10 @@
If we want this flexibility, we will have to complicate our package hierarchy If we want this flexibility, we will have to complicate our package hierarchy
a little. First, we will have to change the name of the extension modules: a little. First, we will have to change the name of the extension modules:
</p> </p>
<pre class="programlisting"><span class="comment">/* file core.cpp */</span> <p>
</p>
<pre class="programlisting">
<span class="comment">/* file core.cpp */</span>
<span class="identifier">BOOST_PYTHON_MODULE</span><span class="special">(</span><span class="identifier">_core</span><span class="special">)</span> <span class="identifier">BOOST_PYTHON_MODULE</span><span class="special">(</span><span class="identifier">_core</span><span class="special">)</span>
<span class="special">{</span> <span class="special">{</span>
<span class="special">...</span> <span class="special">...</span>
@@ -153,7 +162,7 @@
</pre> </pre>
<p> <p>
Note that we added an underscore to the module name. The filename will have Note that we added an underscore to the module name. The filename will have
to be changed to <code class="literal">_core.pyd</code> as well, and we do the same to be changed to <tt class="literal">_core.pyd</tt> as well, and we do the same
to the other extension modules. Now, we change our package hierarchy like to the other extension modules. Now, we change our package hierarchy like
so: so:
</p> </p>
@@ -174,68 +183,77 @@
to each one. But if we leave it that way, the user will have to access the to each one. But if we leave it that way, the user will have to access the
functions in the core module with this syntax: functions in the core module with this syntax:
</p> </p>
<pre class="programlisting"><span class="special">&gt;&gt;&gt;</span> <span class="keyword">import</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">core</span><span class="special">.</span><span class="identifier">_core</span> <p>
</p>
<pre class="programlisting">
<span class="special">&gt;&gt;&gt;</span> <span class="keyword">import</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">core</span><span class="special">.</span><span class="identifier">_core</span>
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">core</span><span class="special">.</span><span class="identifier">_core</span><span class="special">.</span><span class="identifier">foo</span><span class="special">(...)</span> <span class="special">&gt;&gt;&gt;</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">core</span><span class="special">.</span><span class="identifier">_core</span><span class="special">.</span><span class="identifier">foo</span><span class="special">(...)</span>
</pre> </pre>
<p> <p>
which is not what we want. But here enters the <code class="literal">__init__.py</code> which is not what we want. But here enters the <tt class="literal">__init__.py</tt>
magic: everything that is brought to the <code class="literal">__init__.py</code> namespace magic: everything that is brought to the <tt class="literal">__init__.py</tt> namespace
can be accessed directly by the user. So, all we have to do is bring the can be accessed directly by the user. So, all we have to do is bring the
entire namespace from <code class="literal">_core.pyd</code> to <code class="literal">core/__init__.py</code>. entire namespace from <tt class="literal">_core.pyd</tt> to <tt class="literal">core/__init__.py</tt>.
So add this line of code to <code class="literal">sounds/core/__init__.py</code>: So add this line of code to <tt class="literal">sounds<span class="emphasis"><em>core</em></span>__init__.py</tt>:
</p> </p>
<pre class="programlisting"><span class="keyword">from</span> <span class="identifier">_core</span> <span class="keyword">import</span> <span class="special">*</span> <pre class="programlisting">
<span class="keyword">from</span> <span class="identifier">_core</span> <span class="keyword">import</span> <span class="special">*</span>
</pre> </pre>
<p> <p>
We do the same for the other packages. Now the user accesses the functions We do the same for the other packages. Now the user accesses the functions
and classes in the extension modules like before: and classes in the extension modules like before:
</p> </p>
<pre class="programlisting"><span class="special">&gt;&gt;&gt;</span> <span class="keyword">import</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">filters</span> <pre class="programlisting">
<span class="special">&gt;&gt;&gt;</span> <span class="keyword">import</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">filters</span>
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">filters</span><span class="special">.</span><span class="identifier">echo</span><span class="special">(...)</span> <span class="special">&gt;&gt;&gt;</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">filters</span><span class="special">.</span><span class="identifier">echo</span><span class="special">(...)</span>
</pre> </pre>
<p> <p>
with the additional benefit that we can easily add pure Python functions with the additional benefit that we can easily add pure Python functions
to any module, in a way that the user can't tell the difference between a to any module, in a way that the user can't tell the difference between a
C++ function and a Python function. Let's add a <span class="emphasis"><em>pure</em></span> C++ function and a Python function. Let's add a <span class="emphasis"><em>pure</em></span>
Python function, <code class="literal">echo_noise</code>, to the <code class="literal">filters</code> Python function, <tt class="literal">echo_noise</tt>, to the <tt class="literal">filters</tt>
package. This function applies both the <code class="literal">echo</code> and <code class="literal">noise</code> package. This function applies both the <tt class="literal">echo</tt> and <tt class="literal">noise</tt>
filters in sequence in the given <code class="literal">sound</code> object. We create filters in sequence in the given <tt class="literal">sound</tt> object. We create
a file named <code class="literal">sounds/filters/echo_noise.py</code> and code our a file named <tt class="literal">sounds/filters/echo_noise.py</tt> and code our
function: function:
</p> </p>
<pre class="programlisting"><span class="keyword">import</span> <span class="identifier">_filters</span> <pre class="programlisting">
<span class="keyword">import</span> <span class="identifier">_filters</span>
<span class="keyword">def</span> <span class="identifier">echo_noise</span><span class="special">(</span><span class="identifier">sound</span><span class="special">):</span> <span class="keyword">def</span> <span class="identifier">echo_noise</span><span class="special">(</span><span class="identifier">sound</span><span class="special">):</span>
<span class="identifier">s</span> <span class="special">=</span> <span class="identifier">_filters</span><span class="special">.</span><span class="identifier">echo</span><span class="special">(</span><span class="identifier">sound</span><span class="special">)</span> <span class="identifier">s</span> <span class="special">=</span> <span class="identifier">_filters</span><span class="special">.</span><span class="identifier">echo</span><span class="special">(</span><span class="identifier">sound</span><span class="special">)</span>
<span class="identifier">s</span> <span class="special">=</span> <span class="identifier">_filters</span><span class="special">.</span><span class="identifier">noise</span><span class="special">(</span><span class="identifier">sound</span><span class="special">)</span> <span class="identifier">s</span> <span class="special">=</span> <span class="identifier">_filters</span><span class="special">.</span><span class="identifier">noise</span><span class="special">(</span><span class="identifier">sound</span><span class="special">)</span>
<span class="keyword">return</span> <span class="identifier">s</span> <span class="keyword">return</span> <span class="identifier">s</span>
</pre> </pre>
<p> <p>
Next, we add this line to <code class="literal">sounds/filters/__init__.py</code>: Next, we add this line to <tt class="literal">sounds<span class="emphasis"><em>filters</em></span>__init__.py</tt>:
</p> </p>
<pre class="programlisting"><span class="keyword">from</span> <span class="identifier">echo_noise</span> <span class="keyword">import</span> <span class="identifier">echo_noise</span> <pre class="programlisting">
<span class="keyword">from</span> <span class="identifier">echo_noise</span> <span class="keyword">import</span> <span class="identifier">echo_noise</span>
</pre> </pre>
<p> <p>
And that's it. The user now accesses this function like any other function And that's it. The user now accesses this function like any other function
from the <code class="literal">filters</code> package: from the <tt class="literal">filters</tt> package:
</p> </p>
<pre class="programlisting"><span class="special">&gt;&gt;&gt;</span> <span class="keyword">import</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">filters</span> <pre class="programlisting">
<span class="special">&gt;&gt;&gt;</span> <span class="keyword">import</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">filters</span>
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">filters</span><span class="special">.</span><span class="identifier">echo_noise</span><span class="special">(...)</span> <span class="special">&gt;&gt;&gt;</span> <span class="identifier">sounds</span><span class="special">.</span><span class="identifier">filters</span><span class="special">.</span><span class="identifier">echo_noise</span><span class="special">(...)</span>
</pre> </pre>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h3 class="title"> <div class="titlepage"><div><div><h3 class="title">
<a name="python.extending_wrapped_objects_in_python"></a>Extending Wrapped Objects in Python</h3></div></div></div> <a name="python.extending_wrapped_objects_in_python"></a>Extending Wrapped Objects in Python</h3></div></div></div>
<p> <p>
Thanks to Python's flexibility, you can easily add new methods to a class, Thanks to Python's flexibility, you can easily add new methods to a class,
even after it was already created: even after it was already created:
</p> </p>
<pre class="programlisting"><span class="special">&gt;&gt;&gt;</span> <span class="keyword">class</span> <span class="identifier">C</span><span class="special">(</span><span class="identifier">object</span><span class="special">):</span> <span class="keyword">pass</span> <pre class="programlisting">
<span class="special">&gt;&gt;&gt;</span> <span class="keyword">class</span> <span class="identifier">C</span><span class="special">(</span><span class="identifier">object</span><span class="special">):</span> <span class="keyword">pass</span>
<span class="special">&gt;&gt;&gt;</span> <span class="special">&gt;&gt;&gt;</span>
<span class="special">&gt;&gt;&gt;</span> <span class="comment"># a regular function</span> <span class="special">&gt;&gt;&gt;</span> <span class="comment"># a regular function
<span class="special">&gt;&gt;&gt;</span> <span class="keyword">def</span> <span class="identifier">C_str</span><span class="special">(</span><span class="identifier">self</span><span class="special">):</span> <span class="keyword">return</span> <span class="string">'A C instance!'</span> </span><span class="special">&gt;&gt;&gt;</span> <span class="keyword">def</span> <span class="identifier">C_str</span><span class="special">(</span><span class="identifier">self</span><span class="special">):</span> <span class="keyword">return</span> <span class="string">'A C instance!'</span>
<span class="special">&gt;&gt;&gt;</span> <span class="special">&gt;&gt;&gt;</span>
<span class="special">&gt;&gt;&gt;</span> <span class="comment"># now we turn it in a member function</span> <span class="special">&gt;&gt;&gt;</span> <span class="comment"># now we turn it in a member function
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">C</span><span class="special">.</span><span class="identifier">__str__</span> <span class="special">=</span> <span class="identifier">C_str</span> </span><span class="special">&gt;&gt;&gt;</span> <span class="identifier">C</span><span class="special">.</span><span class="identifier">__str__</span> <span class="special">=</span> <span class="identifier">C_str</span>
<span class="special">&gt;&gt;&gt;</span> <span class="special">&gt;&gt;&gt;</span>
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">c</span> <span class="special">=</span> <span class="identifier">C</span><span class="special">()</span> <span class="special">&gt;&gt;&gt;</span> <span class="identifier">c</span> <span class="special">=</span> <span class="identifier">C</span><span class="special">()</span>
<span class="special">&gt;&gt;&gt;</span> <span class="keyword">print</span> <span class="identifier">c</span> <span class="special">&gt;&gt;&gt;</span> <span class="keyword">print</span> <span class="identifier">c</span>
@@ -248,9 +266,12 @@
</p> </p>
<p> <p>
We can do the same with classes that were wrapped with Boost.Python. Suppose We can do the same with classes that were wrapped with Boost.Python. Suppose
we have a class <code class="literal">point</code> in C++: we have a class <tt class="literal">point</tt> in C++:
</p> </p>
<pre class="programlisting"><span class="keyword">class</span> <span class="identifier">point</span> <span class="special">{...};</span> <p>
</p>
<pre class="programlisting">
<span class="keyword">class</span> <span class="identifier">point</span> <span class="special">{...};</span>
<span class="identifier">BOOST_PYTHON_MODULE</span><span class="special">(</span><span class="identifier">_geom</span><span class="special">)</span> <span class="identifier">BOOST_PYTHON_MODULE</span><span class="special">(</span><span class="identifier">_geom</span><span class="special">)</span>
<span class="special">{</span> <span class="special">{</span>
@@ -258,44 +279,48 @@
<span class="special">}</span> <span class="special">}</span>
</pre> </pre>
<p> <p>
If we are using the technique from the previous session, <a class="link" href="techniques.html#python.creating_packages" title="Creating Packages">Creating If we are using the technique from the previous session, <a href="techniques.html#python.creating_packages" title="Creating Packages">Creating
Packages</a>, we can code directly into <code class="literal">geom/__init__.py</code>: Packages</a>, we can code directly into <tt class="literal">geom/__init__.py</tt>:
</p> </p>
<pre class="programlisting"><span class="keyword">from</span> <span class="identifier">_geom</span> <span class="keyword">import</span> <span class="special">*</span> <p>
</p>
<pre class="programlisting">
<span class="keyword">from</span> <span class="identifier">_geom</span> <span class="keyword">import</span> <span class="special">*</span>
<span class="comment"># a regular function</span> <span class="comment"># a regular function
<span class="keyword">def</span> <span class="identifier">point_str</span><span class="special">(</span><span class="identifier">self</span><span class="special">):</span> </span><span class="keyword">def</span> <span class="identifier">point_str</span><span class="special">(</span><span class="identifier">self</span><span class="special">):</span>
<span class="keyword">return</span> <span class="identifier">str</span><span class="special">((</span><span class="identifier">self</span><span class="special">.</span><span class="identifier">x</span><span class="special">,</span> <span class="identifier">self</span><span class="special">.</span><span class="identifier">y</span><span class="special">))</span> <span class="keyword">return</span> <span class="identifier">str</span><span class="special">((</span><span class="identifier">self</span><span class="special">.</span><span class="identifier">x</span><span class="special">,</span> <span class="identifier">self</span><span class="special">.</span><span class="identifier">y</span><span class="special">))</span>
<span class="comment"># now we turn it into a member function</span> <span class="comment"># now we turn it into a member function
<span class="identifier">point</span><span class="special">.</span><span class="identifier">__str__</span> <span class="special">=</span> <span class="identifier">point_str</span> </span><span class="identifier">point</span><span class="special">.</span><span class="identifier">__str__</span> <span class="special">=</span> <span class="identifier">point_str</span>
</pre> </pre>
<p> <p>
<span class="bold"><strong>All</strong></span> point instances created from C++ will <span class="bold"><b>All</b></span> point instances created from C++ will
also have this member function! This technique has several advantages: also have this member function! This technique has several advantages:
</p> </p>
<div class="itemizedlist"><ul class="itemizedlist" type="disc"> <div class="itemizedlist"><ul type="disc">
<li class="listitem"> <li>
Cut down compile times to zero for these additional functions Cut down compile times to zero for these additional functions
</li> </li>
<li class="listitem"> <li>
Reduce the memory footprint to virtually zero Reduce the memory footprint to virtually zero
</li> </li>
<li class="listitem"> <li>
Minimize the need to recompile Minimize the need to recompile
</li> </li>
<li class="listitem"> <li>
Rapid prototyping (you can move the code to C++ if required without changing Rapid prototyping (you can move the code to C++ if required without changing
the interface) the interface)
</li> </li>
</ul></div> </ul></div>
<p> <p>
You can even add a little syntactic sugar with the use of metaclasses. Let's You can even add a little syntactic sugar with the use of metaclasses. Let's
create a special metaclass that "injects" methods in other classes. create a special metaclass that "injects" methods in other classes.
</p> </p>
<pre class="programlisting"><span class="comment"># The one Boost.Python uses for all wrapped classes.</span> <pre class="programlisting">
<span class="comment"># You can use here any class exported by Boost instead of "point"</span> <span class="comment"># The one Boost.Python uses for all wrapped classes.
<span class="identifier">BoostPythonMetaclass</span> <span class="special">=</span> <span class="identifier">point</span><span class="special">.</span><span class="identifier">__class__</span> </span><span class="comment"># You can use here any class exported by Boost instead of "point"
</span><span class="identifier">BoostPythonMetaclass</span> <span class="special">=</span> <span class="identifier">point</span><span class="special">.</span><span class="identifier">__class__</span>
<span class="keyword">class</span> <span class="identifier">injector</span><span class="special">(</span><span class="identifier">object</span><span class="special">):</span> <span class="keyword">class</span> <span class="identifier">injector</span><span class="special">(</span><span class="identifier">object</span><span class="special">):</span>
<span class="keyword">class</span> <span class="identifier">__metaclass__</span><span class="special">(</span><span class="identifier">BoostPythonMetaclass</span><span class="special">):</span> <span class="keyword">class</span> <span class="identifier">__metaclass__</span><span class="special">(</span><span class="identifier">BoostPythonMetaclass</span><span class="special">):</span>
@@ -306,8 +331,8 @@
<span class="identifier">setattr</span><span class="special">(</span><span class="identifier">b</span><span class="special">,</span><span class="identifier">k</span><span class="special">,</span><span class="identifier">v</span><span class="special">)</span> <span class="identifier">setattr</span><span class="special">(</span><span class="identifier">b</span><span class="special">,</span><span class="identifier">k</span><span class="special">,</span><span class="identifier">v</span><span class="special">)</span>
<span class="keyword">return</span> <span class="identifier">type</span><span class="special">.</span><span class="identifier">__init__</span><span class="special">(</span><span class="identifier">self</span><span class="special">,</span> <span class="identifier">name</span><span class="special">,</span> <span class="identifier">bases</span><span class="special">,</span> <span class="identifier">dict</span><span class="special">)</span> <span class="keyword">return</span> <span class="identifier">type</span><span class="special">.</span><span class="identifier">__init__</span><span class="special">(</span><span class="identifier">self</span><span class="special">,</span> <span class="identifier">name</span><span class="special">,</span> <span class="identifier">bases</span><span class="special">,</span> <span class="identifier">dict</span><span class="special">)</span>
<span class="comment"># inject some methods in the point foo</span> <span class="comment"># inject some methods in the point foo
<span class="keyword">class</span> <span class="identifier">more_point</span><span class="special">(</span><span class="identifier">injector</span><span class="special">,</span> <span class="identifier">point</span><span class="special">):</span> </span><span class="keyword">class</span> <span class="identifier">more_point</span><span class="special">(</span><span class="identifier">injector</span><span class="special">,</span> <span class="identifier">point</span><span class="special">):</span>
<span class="keyword">def</span> <span class="identifier">__repr__</span><span class="special">(</span><span class="identifier">self</span><span class="special">):</span> <span class="keyword">def</span> <span class="identifier">__repr__</span><span class="special">(</span><span class="identifier">self</span><span class="special">):</span>
<span class="keyword">return</span> <span class="string">'Point(x=%s, y=%s)'</span> <span class="special">%</span> <span class="special">(</span><span class="identifier">self</span><span class="special">.</span><span class="identifier">x</span><span class="special">,</span> <span class="identifier">self</span><span class="special">.</span><span class="identifier">y</span><span class="special">)</span> <span class="keyword">return</span> <span class="string">'Point(x=%s, y=%s)'</span> <span class="special">%</span> <span class="special">(</span><span class="identifier">self</span><span class="special">.</span><span class="identifier">x</span><span class="special">,</span> <span class="identifier">self</span><span class="special">.</span><span class="identifier">y</span><span class="special">)</span>
<span class="keyword">def</span> <span class="identifier">foo</span><span class="special">(</span><span class="identifier">self</span><span class="special">):</span> <span class="keyword">def</span> <span class="identifier">foo</span><span class="special">(</span><span class="identifier">self</span><span class="special">):</span>
@@ -316,7 +341,8 @@
<p> <p>
Now let's see how it got: Now let's see how it got:
</p> </p>
<pre class="programlisting"><span class="special">&gt;&gt;&gt;</span> <span class="keyword">print</span> <span class="identifier">point</span><span class="special">()</span> <pre class="programlisting">
<span class="special">&gt;&gt;&gt;</span> <span class="keyword">print</span> <span class="identifier">point</span><span class="special">()</span>
<span class="identifier">Point</span><span class="special">(</span><span class="identifier">x</span><span class="special">=</span><span class="number">10</span><span class="special">,</span> <span class="identifier">y</span><span class="special">=</span><span class="number">10</span><span class="special">)</span> <span class="identifier">Point</span><span class="special">(</span><span class="identifier">x</span><span class="special">=</span><span class="number">10</span><span class="special">,</span> <span class="identifier">y</span><span class="special">=</span><span class="number">10</span><span class="special">)</span>
<span class="special">&gt;&gt;&gt;</span> <span class="identifier">point</span><span class="special">().</span><span class="identifier">foo</span><span class="special">()</span> <span class="special">&gt;&gt;&gt;</span> <span class="identifier">point</span><span class="special">().</span><span class="identifier">foo</span><span class="special">()</span>
<span class="identifier">foo</span><span class="special">!</span> <span class="identifier">foo</span><span class="special">!</span>
@@ -324,7 +350,8 @@
<p> <p>
Another useful idea is to replace constructors with factory functions: Another useful idea is to replace constructors with factory functions:
</p> </p>
<pre class="programlisting"><span class="identifier">_point</span> <span class="special">=</span> <span class="identifier">point</span> <pre class="programlisting">
<span class="identifier">_point</span> <span class="special">=</span> <span class="identifier">point</span>
<span class="keyword">def</span> <span class="identifier">point</span><span class="special">(</span><span class="identifier">x</span><span class="special">=</span><span class="number">0</span><span class="special">,</span> <span class="identifier">y</span><span class="special">=</span><span class="number">0</span><span class="special">):</span> <span class="keyword">def</span> <span class="identifier">point</span><span class="special">(</span><span class="identifier">x</span><span class="special">=</span><span class="number">0</span><span class="special">,</span> <span class="identifier">y</span><span class="special">=</span><span class="number">0</span><span class="special">):</span>
<span class="keyword">return</span> <span class="identifier">_point</span><span class="special">(</span><span class="identifier">x</span><span class="special">,</span> <span class="identifier">y</span><span class="special">)</span> <span class="keyword">return</span> <span class="identifier">_point</span><span class="special">(</span><span class="identifier">x</span><span class="special">,</span> <span class="identifier">y</span><span class="special">)</span>
@@ -336,7 +363,7 @@
support. support.
</p> </p>
</div> </div>
<div class="section"> <div class="section" lang="en">
<div class="titlepage"><div><div><h3 class="title"> <div class="titlepage"><div><div><h3 class="title">
<a name="python.reducing_compiling_time"></a>Reducing Compiling Time</h3></div></div></div> <a name="python.reducing_compiling_time"></a>Reducing Compiling Time</h3></div></div></div>
<p> <p>
@@ -345,7 +372,10 @@
can easily become too high. If this is causing you problems, you can split can easily become too high. If this is causing you problems, you can split
the class_ definitions in multiple files: the class_ definitions in multiple files:
</p> </p>
<pre class="programlisting"><span class="comment">/* file point.cpp */</span> <p>
</p>
<pre class="programlisting">
<span class="comment">/* file point.cpp */</span>
<span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">point</span><span class="special">.</span><span class="identifier">h</span><span class="special">&gt;</span> <span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">point</span><span class="special">.</span><span class="identifier">h</span><span class="special">&gt;</span>
<span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">python</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span> <span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">python</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span>
@@ -364,10 +394,11 @@
<span class="special">}</span> <span class="special">}</span>
</pre> </pre>
<p> <p>
Now you create a file <code class="literal">main.cpp</code>, which contains the <code class="literal">BOOST_PYTHON_MODULE</code> Now you create a file <tt class="literal">main.cpp</tt>, which contains the <tt class="literal">BOOST_PYTHON_MODULE</tt>
macro, and call the various export functions inside it. macro, and call the various export functions inside it.
</p> </p>
<pre class="programlisting"><span class="keyword">void</span> <span class="identifier">export_point</span><span class="special">();</span> <pre class="programlisting">
<span class="keyword">void</span> <span class="identifier">export_point</span><span class="special">();</span>
<span class="keyword">void</span> <span class="identifier">export_triangle</span><span class="special">();</span> <span class="keyword">void</span> <span class="identifier">export_triangle</span><span class="special">();</span>
<span class="identifier">BOOST_PYTHON_MODULE</span><span class="special">(</span><span class="identifier">_geom</span><span class="special">)</span> <span class="identifier">BOOST_PYTHON_MODULE</span><span class="special">(</span><span class="identifier">_geom</span><span class="special">)</span>
@@ -380,7 +411,8 @@
Compiling and linking together all this files produces the same result as Compiling and linking together all this files produces the same result as
the usual approach: the usual approach:
</p> </p>
<pre class="programlisting"><span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">python</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span> <pre class="programlisting">
<span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">python</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span>
<span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">point</span><span class="special">.</span><span class="identifier">h</span><span class="special">&gt;</span> <span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">point</span><span class="special">.</span><span class="identifier">h</span><span class="special">&gt;</span>
<span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">triangle</span><span class="special">.</span><span class="identifier">h</span><span class="special">&gt;</span> <span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">triangle</span><span class="special">.</span><span class="identifier">h</span><span class="special">&gt;</span>
@@ -400,21 +432,21 @@
</p> </p>
<div class="note"><table border="0" summary="Note"> <div class="note"><table border="0" summary="Note">
<tr> <tr>
<td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../../../doc/src/images/note.png"></td> <td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../../../doc/html/images/note.png"></td>
<th align="left">Note</th> <th align="left">Note</th>
</tr> </tr>
<tr><td align="left" valign="top"><p> <tr><td colspan="2" align="left" valign="top"><p>
If you're exporting your classes with <a href="../../../../../pyste/index.html" target="_top">Pyste</a>, If you're exporting your classes with <a href="../../../../../pyste/index.html" target="_top">Pyste</a>,
take a look at the <code class="literal">--multiple</code> option, that generates take a look at the <tt class="literal">--multiple</tt> option, that generates
the wrappers in various files as demonstrated here. the wrappers in various files as demonstrated here.
</p></td></tr> </p></td></tr>
</table></div> </table></div>
<div class="note"><table border="0" summary="Note"> <div class="note"><table border="0" summary="Note">
<tr> <tr>
<td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../../../doc/src/images/note.png"></td> <td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../../../doc/html/images/note.png"></td>
<th align="left">Note</th> <th align="left">Note</th>
</tr> </tr>
<tr><td align="left" valign="top"><p> <tr><td colspan="2" align="left" valign="top"><p>
This method is useful too if you are getting the error message <span class="emphasis"><em>"fatal This method is useful too if you are getting the error message <span class="emphasis"><em>"fatal
error C1204:Compiler limit:internal structure overflow"</em></span> error C1204:Compiler limit:internal structure overflow"</em></span>
when compiling a large source file, as explained in the <a href="../../../../v2/faq.html#c1204" target="_top">FAQ</a>. when compiling a large source file, as explained in the <a href="../../../../v2/faq.html#c1204" target="_top">FAQ</a>.
@@ -424,7 +456,7 @@
</div> </div>
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr> <table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
<td align="left"></td> <td align="left"></td>
<td align="right"><div class="copyright-footer">Copyright &#169; 2002-2005 Joel <td align="right"><div class="copyright-footer">Copyright © 2002-2005 Joel
de Guzman, David Abrahams<p> de Guzman, David Abrahams<p>
Distributed under the Boost Software License, Version 1.0. (See accompanying Distributed under the Boost Software License, Version 1.0. (See accompanying
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top"> file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">
@@ -434,7 +466,7 @@
</tr></table> </tr></table>
<hr> <hr>
<div class="spirit-nav"> <div class="spirit-nav">
<a accesskey="p" href="exception.html"><img src="../../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/src/images/home.png" alt="Home"></a> <a accesskey="p" href="exception.html"><img src="../../../../../../../doc/html/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../../../doc/html/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../../../doc/html/images/home.png" alt="Home"></a>
</div> </div>
</body> </body>
</html> </html>

View File

@@ -1,5 +1,5 @@
[library python [library python
[version 2.0] [version 1.0]
[authors [de Guzman, Joel], [Abrahams, David]] [authors [de Guzman, Joel], [Abrahams, David]]
[copyright 2002 2003 2004 2005 Joel de Guzman, David Abrahams] [copyright 2002 2003 2004 2005 Joel de Guzman, David Abrahams]
[category inter-language support] [category inter-language support]
@@ -62,7 +62,7 @@ resulting DLL is now visible to Python. Here's a sample Python session:
[python] [python]
>>> import hello_ext >>> import hello_ext
>>> print hello_ext.greet() >>> print hello.greet()
hello, world hello, world
[c++] [c++]
@@ -901,8 +901,8 @@ wrapping as outlined in the [link python.overloading previous section], or
writing thin wrappers: writing thin wrappers:
// write "thin wrappers" // write "thin wrappers"
int f1(int x) { return f(x); } int f1(int x) { f(x); }
int f2(int x, double y) { return f(x,y); } int f2(int x, double y) { f(x,y); }
/*...*/ /*...*/
@@ -1302,23 +1302,6 @@ create a new scope around a class:
[def PyModule_GetDict [@http://www.python.org/doc/current/api/moduleObjects.html#l2h-594 PyModule_GetDict]] [def PyModule_GetDict [@http://www.python.org/doc/current/api/moduleObjects.html#l2h-594 PyModule_GetDict]]
[endsect] [endsect]
[section:creating_python_object Creating `boost::python::object` from `PyObject*`]
When you want a `boost::python::object` to manage a pointer to `PyObject*` pyobj one does:
boost::python::object o(boost::python::handle<>(pyobj));
In this case, the `o` object, manages the `pyobj`, it wont increase the reference count on construction.
Otherwise, to use a borrowed reference:
boost::python::object o(boost::python::handle<>(boost::python::borrowed(pyobj)));
In this case, `Py_INCREF` is called, so `pyobj` is not destructed when object o goes out of scope.
[endsect] [/ creating_python_object ]
[endsect] [/ Object Interface] [endsect] [/ Object Interface]
[section Embedding] [section Embedding]
@@ -1398,10 +1381,10 @@ interpreter. This may be fixed in a future version of boost.python.]
[section Using the interpreter] [section Using the interpreter]
As you probably already know, objects in Python are reference-counted. As you probably already know, objects in Python are reference-counted.
Naturally, the [^PyObject]s of the Python C API are also reference-counted. Naturally, the [^PyObject]s of the Python\/C API are also reference-counted.
There is a difference however. While the reference-counting is fully There is a difference however. While the reference-counting is fully
automatic in Python, the Python C API requires you to do it automatic in Python, the Python\/C API requires you to do it
[@http://www.python.org/doc/current/c-api/refcounting.html by hand]. This is [@http://www.python.org/doc/current/api/refcounts.html by hand]. This is
messy and especially hard to get right in the presence of C++ exceptions. messy and especially hard to get right in the presence of C++ exceptions.
Fortunately Boost.Python provides the [@../../../v2/handle.html handle] and Fortunately Boost.Python provides the [@../../../v2/handle.html handle] and
[@../../../v2/object.html object] class templates to automate the process. [@../../../v2/object.html object] class templates to automate the process.
@@ -1483,7 +1466,7 @@ If an exception occurs in the evaluation of the python expression,
The [^error_already_set] exception class doesn't carry any information in itself. The [^error_already_set] exception class doesn't carry any information in itself.
To find out more about the Python exception that occurred, you need to use the To find out more about the Python exception that occurred, you need to use the
[@http://www.python.org/doc/api/exceptionHandling.html exception handling functions] [@http://www.python.org/doc/api/exceptionHandling.html exception handling functions]
of the Python C API in your catch-statement. This can be as simple as calling of the Python/C API in your catch-statement. This can be as simple as calling
[@http://www.python.org/doc/api/exceptionHandling.html#l2h-70 PyErr_Print()] to [@http://www.python.org/doc/api/exceptionHandling.html#l2h-70 PyErr_Print()] to
print the exception's traceback to the console, or comparing the type of the print the exception's traceback to the console, or comparing the type of the
exception with those of the [@http://www.python.org/doc/api/standardExceptions.html exception with those of the [@http://www.python.org/doc/api/standardExceptions.html

View File

@@ -137,7 +137,7 @@
<td valign="top"><code>P::extract_return_type</code></td> <td valign="top"><code>P::extract_return_type</code></td>
<td>A model of <a href= <td>A model of <a href=
"../../../mpl/doc/refmanual/metafunction.html">Metafunction</a>.</td> "../../../doc/refmanual/metafunction.html">Metafunction</a>.</td>
<td>An MPL unary <a href= <td>An MPL unary <a href=
"../../../mpl/doc/refmanual/metafunction.html">Metafunction</a> used extract the return type from a given signature. By default it is derived from mpl::front.</td> "../../../mpl/doc/refmanual/metafunction.html">Metafunction</a> used extract the return type from a given signature. By default it is derived from mpl::front.</td>

View File

@@ -101,7 +101,7 @@ namespace boost { namespace python
struct arg struct arg
{ {
template &lt;class T&gt; template &lt;class T&gt;
arg &amp;operator = (T const &amp;value); arg &amp;perator = (T const &amp;value);
explicit arg (char const *name){elements[0].name = name;} explicit arg (char const *name){elements[0].name = name;}
}; };

View File

@@ -106,33 +106,6 @@
function from being treated as an exported symbol on platforms which function from being treated as an exported symbol on platforms which
support that distinction in-code</td> support that distinction in-code</td>
</tr> </tr>
<tr>
<td valign="top"><code>BOOST_PYTHON_ENABLE_CDECL</code></td>
<td valign="top" align="center"><i>not&nbsp;defined</i></td>
<td valign="top">If defined, allows functions using the <code>__cdecl
</code> calling convention to be wrapped.</td>
</tr>
<tr>
<td valign="top"><code>BOOST_PYTHON_ENABLE_STDCALL</code></td>
<td valign="top" align="center"><i>not&nbsp;defined</i></td>
<td valign="top">If defined, allows functions using the <code>__stdcall
</code> calling convention to be wrapped.</td>
</tr>
<tr>
<td valign="top"><code>BOOST_PYTHON_ENABLE_FASTCALL</code></td>
<td valign="top" align="center"><i>not&nbsp;defined</i></td>
<td valign="top">If defined, allows functions using the <code>__fastcall
</code> calling convention to be wrapped.</td>
</tr>
</table> </table>
<h2><a name="lib-defined-impl"></a>Library Defined Implementation <h2><a name="lib-defined-impl"></a>Library Defined Implementation

0
doc/v2/instance_holder.html Executable file → Normal file
View File

0
doc/v2/lvalue_from_pytype.html Executable file → Normal file
View File

View File

@@ -96,10 +96,10 @@ template &lt;class F, class Policies, class Keywords, class Signature&gt;
to <code>f</code>. <ul> to <code>f</code>. <ul>
<li> If <code>policies</code> are supplied, it <li> If <code>policies</code> are supplied, it
will be applied to the function as described <a href= will be applied to the function as described <a href=
"CallPolicies.html">here</a>. "CallPolicies.html">here</a>.
<li>If <code>keywords</code> are <li>If <code>keywords</code> are
supplied, the keywords will be applied in order to the final supplied, the keywords will be applied in order to the final
arguments of the resulting function. arguments of the resulting function.
<li>If <code>Signature</code> <li>If <code>Signature</code>
is supplied, it should be an instance of an <a is supplied, it should be an instance of an <a
href="../../../mpl/doc/refmanual/front-extensible-sequence.html">MPL front-extensible href="../../../mpl/doc/refmanual/front-extensible-sequence.html">MPL front-extensible
@@ -125,33 +125,36 @@ template &lt;class F, class Policies, class Keywords, class Signature&gt;
</dl> </dl>
<pre> <pre>
<a name="make_constructor-spec">template &lt;class F&gt;</a> <a name=
<a href="object.html#object-spec">object</a> make_constructor(F f) "make_constructor-spec"></a>template &lt;class T, class ArgList, class Generator&gt;
<a href="object.html#object-spec">object</a> make_constructor();
template &lt;class F, class Policies&gt;
template &lt;class ArgList, class Generator, class Policies&gt;
<a href= <a href=
"object.html#object-spec">object</a> make_constructor(F f, Policies const&amp; policies) "object.html#object-spec">object</a> make_constructor(Policies const&amp; policies)
template &lt;class F, class Policies, class KeywordsOrSignature&gt;
<a href=
"object.html#object-spec">object</a> make_constructor(F f, Policies const&amp; policies, KeywordsOrSignature const&amp; ks)
template &lt;class F, class Policies, class Keywords, class Signature&gt;
<a href=
"object.html#object-spec">object</a> make_constructor(F f, Policies const&amp; policies, Keywords const&amp; kw, Signature const&amp; sig)
</pre> </pre>
<dl class="function-semantics"> <dl class="function-semantics">
<dt><b>Requires:</b> <code>F</code> is a <dt><b>Requires:</b> <code>T</code> is a class type.
function pointer type. If <code>policies</code> are supplied, it must <code>Policies</code> is a model of <a href=
be a model of <a href="CallPolicies.html">CallPolicies</a>. If "CallPolicies.html">CallPolicies</a>. <code>ArgList</code> is an <a
<code>kewords</code> are supplied, it must be the result of a <a href= href="../../../mpl/doc/refmanual/forward-sequence.html">MPL sequence</a> of C++ argument
"args.html#keyword-expression"><em>keyword-expression</em></a> types (<i>A1,&nbsp;A2,...&nbsp;AN</i>) such that if
specifying no more arguments than the <a href= <code>a1,&nbsp;a2</code>...&nbsp;<code>aN</code> are objects of type
"definitions.html#arity">arity</a> of <code>f</code>.</dt> <i>A1,&nbsp;A2,...&nbsp;AN</i> respectively, the expression <code>new
Generator::apply&lt;T&gt;::type(a1,&nbsp;a2</code>...&nbsp;<code>aN</code>)
is valid. Generator is a model of <a href=
"HolderGenerator.html">HolderGenerator</a>.</dt>
<dt><b>Effects:</b> Creates a Python callable object which, when called <dt><b>Effects:</b> Creates a Python callable object which, when called
from Python, converts its arguments to C++ and calls <code>f</code>.</dt> from Python, expects its first argument to be a Boost.Python extension
class object. It converts its remaining its arguments to C++ and passes
them to the constructor of a dynamically-allocated
<code>Generator::apply&lt;T&gt;::type</code> object, which is then
installed in the extension class object. In the second form, the
<code>policies</code> are applied to the arguments and result (<a href=
"http://www.python.org/doc/current/lib/bltin-null-object.html">None</a>)
of the Python callable object</dt>
<dt><b>Returns:</b> An instance of <a href= <dt><b>Returns:</b> An instance of <a href=
"object.html#object-spec">object</a> which holds the new Python "object.html#object-spec">object</a> which holds the new Python
@@ -183,7 +186,7 @@ BOOST_PYTHON_MODULE(make_function_test)
def("choose_function", choose_function); def("choose_function", choose_function);
} }
</pre> </pre>
It can be used this way in Python: It can be used this way in Python:
<pre> <pre>
&gt;&gt;&gt; from make_function_test import * &gt;&gt;&gt; from make_function_test import *
&gt;&gt;&gt; f = choose_function(1) &gt;&gt;&gt; f = choose_function(1)

View File

@@ -655,11 +655,6 @@ namespace boost { namespace python { namespace api
template &lt;class A0, class A1,...class An&gt; template &lt;class A0, class A1,...class An&gt;
object operator()(A0 const&amp;, A1 const&amp;,...An const&amp;) const; object operator()(A0 const&amp;, A1 const&amp;,...An const&amp;) const;
detail::args_proxy operator* () const;
object operator()(detail::args_proxy const &amp;args) const;
object operator()(detail::args_proxy const &amp;args,
detail::kwds_proxy const &amp;kwds) const;
// truth value testing // truth value testing
// //
typedef unspecified bool_type; typedef unspecified bool_type;
@@ -709,25 +704,6 @@ object operator()(A0 const&amp; a1, A1 const&amp; a2,...An const&amp; aN) const;
call&lt;object&gt;(object(*static_cast&lt;U*&gt;(this)).ptr(), a1, call&lt;object&gt;(object(*static_cast&lt;U*&gt;(this)).ptr(), a1,
a2,...aN)</dt> a2,...aN)</dt>
</dl> </dl>
<pre>
object operator()(detail::args_proxy const &amp;args) const;
</pre>
<dl class="function-semantics">
<dt><b>Effects:</b>
call object with arguments given by the tuple <varname>args</varname></dt>
</dl>
<pre>
object operator()(detail::args_proxy const &amp;args,
detail::kwds_proxy const &amp;kwds) const;
</pre>
<dl class="function-semantics">
<dt><b>Effects:</b>
call object with arguments given by the tuple <varname>args</varname>, and named
arguments given by the dictionary <varname>kwds</varname></dt>
</dl>
<pre> <pre>
operator bool_type() const; operator bool_type() const;
</pre> </pre>
@@ -835,8 +811,6 @@ namespace boost { namespace python { namespace api
object&amp; operator=(object const&amp;); object&amp; operator=(object const&amp;);
PyObject* ptr() const; PyObject* ptr() const;
bool is_none() const;
}; };
}}} }}}
</pre> </pre>
@@ -897,14 +871,6 @@ PyObject* ptr() const;
<dt><b>Returns:</b> a pointer to the internally-held Python <dt><b>Returns:</b> a pointer to the internally-held Python
object.</dt> object.</dt>
</dl> </dl>
<pre>
bool is_none() const;
</pre>
<dl class="function-semantics">
<dt><b>Returns:</b> result of (ptr() == Py_None)</dt>
</dl>
<!-- --> <!-- -->
<h3><a name="proxy-spec"></a>Class template <code>proxy</code></h3> <h3><a name="proxy-spec"></a>Class template <code>proxy</code></h3>
@@ -1111,7 +1077,7 @@ object sum_items(object seq)
</pre> </pre>
<p>Revised <p>Revised
<!--webbot bot="Timestamp" S-Type="EDITED" S-Format="%d %B, %Y" startspan --> <!--webbot bot="Timestamp" S-Type="EDITED" S-Format="%d %B, %Y" startspan -->
15 March, 2010 27 May, 2008
<!--webbot bot="Timestamp" endspan i-checksum="39359" --> <!--webbot bot="Timestamp" endspan i-checksum="39359" -->
</p> </p>

0
doc/v2/operators.html Executable file → Normal file
View File

View File

@@ -1,93 +1,112 @@
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.0//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> "http://www.w3.org/TR/REC-html40/strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"> <title>Boost.Python Pickle Support</title>
<head>
<title>Boost.Python Pickle Support</title>
</head>
<body> <div>
<div>
<img src="../../../../boost.png" alt="boost.png (6897 bytes)" align=
"center" width="277" height="86" />
<hr />
<h1>Boost.Python Pickle Support</h1>Pickle is a Python module for object <img src="../../../../boost.png"
serialization, also known as persistence, marshalling, or flattening. alt="boost.png (6897 bytes)"
align="center"
width="277" height="86">
<p>It is often necessary to save and restore the contents of an object to <hr>
a file. One approach to this problem is to write a pair of functions that <h1>Boost.Python Pickle Support</h1>
read and write data from a file in a special format. A powerful
alternative approach is to use Python's pickle module. Exploiting
Python's ability for introspection, the pickle module recursively
converts nearly arbitrary Python objects into a stream of bytes that can
be written to a file.</p>
<p>The Boost Python Library supports the pickle module through the Pickle is a Python module for object serialization, also known
interface as described in detail in the <a href= as persistence, marshalling, or flattening.
"http://www.python.org/doc/current/lib/module-pickle.html">Python Library
Reference for pickle.</a> This interface involves the special methods
<tt>__getinitargs__</tt>, <tt>__getstate__</tt> and <tt>__setstate__</tt>
as described in the following. Note that Boost.Python is also fully
compatible with Python's cPickle module.</p>
<hr />
<h2>The Boost.Python Pickle Interface</h2>At the user level, the <p>
Boost.Python pickle interface involves three special methods: It is often necessary to save and restore the contents of an object to
a file. One approach to this problem is to write a pair of functions
that read and write data from a file in a special format. A powerful
alternative approach is to use Python's pickle module. Exploiting
Python's ability for introspection, the pickle module recursively
converts nearly arbitrary Python objects into a stream of bytes that
can be written to a file.
<dl> <p>
<dt><strong><tt>__getinitargs__</tt></strong></dt> The Boost Python Library supports the pickle module
through the interface as described in detail in the
<a href="http://www.python.org/doc/current/lib/module-pickle.html"
>Python Library Reference for pickle.</a> This interface
involves the special methods <tt>__getinitargs__</tt>,
<tt>__getstate__</tt> and <tt>__setstate__</tt> as described
in the following. Note that Boost.Python is also fully compatible
with Python's cPickle module.
<dd> <hr>
When an instance of a Boost.Python extension class is pickled, the <h2>The Boost.Python Pickle Interface</h2>
pickler tests if the instance has a <tt>__getinitargs__</tt> method.
This method must return a Python tuple (it is most convenient to use
a boost::python::tuple). When the instance is restored by the
unpickler, the contents of this tuple are used as the arguments for
the class constructor.
<p>If <tt>__getinitargs__</tt> is not defined, <tt>pickle.load</tt> At the user level, the Boost.Python pickle interface involves three special
will call the constructor (<tt>__init__</tt>) without arguments; methods:
i.e., the object must be default-constructible.</p>
</dd>
<dt><strong><tt>__getstate__</tt></strong></dt> <dl>
<dt>
<strong><tt>__getinitargs__</tt></strong>
<dd>
When an instance of a Boost.Python extension class is pickled, the
pickler tests if the instance has a <tt>__getinitargs__</tt> method.
This method must return a Python tuple (it is most convenient to use
a boost::python::tuple). When the instance is restored by the
unpickler, the contents of this tuple are used as the arguments for
the class constructor.
<dd>When an instance of a Boost.Python extension class is pickled, the <p>
pickler tests if the instance has a <tt>__getstate__</tt> method. This If <tt>__getinitargs__</tt> is not defined, <tt>pickle.load</tt>
method should return a Python object representing the state of the will call the constructor (<tt>__init__</tt>) without arguments;
instance.</dd> i.e., the object must be default-constructible.
<dt><strong><tt>__setstate__</tt></strong></dt> <p>
<dt>
<strong><tt>__getstate__</tt></strong>
<dd>When an instance of a Boost.Python extension class is restored by <dd>
the unpickler (<tt>pickle.load</tt>), it is first constructed using the When an instance of a Boost.Python extension class is pickled, the
result of <tt>__getinitargs__</tt> as arguments (see above). pickler tests if the instance has a <tt>__getstate__</tt> method.
Subsequently the unpickler tests if the new instance has a This method should return a Python object representing the state of
<tt>__setstate__</tt> method. If so, this method is called with the the instance.
result of <tt>__getstate__</tt> (a Python object) as the argument.</dd>
</dl>The three special methods described above may be <tt>.def()</tt>'ed
individually by the user. However, Boost.Python provides an easy to use
high-level interface via the
<strong><tt>boost::python::pickle_suite</tt></strong> class that also
enforces consistency: <tt>__getstate__</tt> and <tt>__setstate__</tt>
must be defined as pairs. Use of this interface is demonstrated by the
following examples.
<hr />
<h2>Examples</h2>There are three files in <tt>boost/libs/python/test</tt> <p>
that show how to provide pickle support. <dt>
<hr /> <strong><tt>__setstate__</tt></strong>
<h3><a href="../../test/pickle1.cpp"><tt>pickle1.cpp</tt></a></h3>The C++ <dd>
class in this example can be fully restored by passing the appropriate When an instance of a Boost.Python extension class is restored by the
argument to the constructor. Therefore it is sufficient to define the unpickler (<tt>pickle.load</tt>), it is first constructed using the
pickle interface method <tt>__getinitargs__</tt>. This is done in the result of <tt>__getinitargs__</tt> as arguments (see above). Subsequently
following way: the unpickler tests if the new instance has a <tt>__setstate__</tt>
method. If so, this method is called with the result of
<tt>__getstate__</tt> (a Python object) as the argument.
<ul> </dl>
<li>1. Definition of the C++ pickle function:
<pre> The three special methods described above may be <tt>.def()</tt>'ed
individually by the user. However, Boost.Python provides an easy to use
high-level interface via the
<strong><tt>boost::python::pickle_suite</tt></strong> class that also
enforces consistency: <tt>__getstate__</tt> and <tt>__setstate__</tt>
must be defined as pairs. Use of this interface is demonstrated by the
following examples.
<hr>
<h2>Examples</h2>
There are three files in
<tt>boost/libs/python/test</tt> that show how to
provide pickle support.
<hr>
<h3><a href="../../test/pickle1.cpp"><tt>pickle1.cpp</tt></a></h3>
The C++ class in this example can be fully restored by passing the
appropriate argument to the constructor. Therefore it is sufficient
to define the pickle interface method <tt>__getinitargs__</tt>.
This is done in the following way:
<ul>
<li>1. Definition of the C++ pickle function:
<pre>
struct world_pickle_suite : boost::python::pickle_suite struct world_pickle_suite : boost::python::pickle_suite
{ {
static static
@@ -98,28 +117,26 @@
} }
}; };
</pre> </pre>
</li> <li>2. Establishing the Python binding:
<pre>
<li>2. Establishing the Python binding:
<pre>
class_&lt;world&gt;("world", args&lt;const std::string&amp;&gt;()) class_&lt;world&gt;("world", args&lt;const std::string&amp;&gt;())
// ... // ...
.def_pickle(world_pickle_suite()) .def_pickle(world_pickle_suite())
// ... // ...
</pre> </pre>
</li> </ul>
</ul>
<hr />
<h3><a href="../../test/pickle2.cpp"><tt>pickle2.cpp</tt></a></h3>The C++ <hr>
class in this example contains member data that cannot be restored by any <h3><a href="../../test/pickle2.cpp"><tt>pickle2.cpp</tt></a></h3>
of the constructors. Therefore it is necessary to provide the
<tt>__getstate__</tt>/<tt>__setstate__</tt> pair of pickle interface
methods:
<ul> The C++ class in this example contains member data that cannot be
<li>1. Definition of the C++ pickle functions: restored by any of the constructors. Therefore it is necessary to
<pre> provide the <tt>__getstate__</tt>/<tt>__setstate__</tt> pair of
pickle interface methods:
<ul>
<li>1. Definition of the C++ pickle functions:
<pre>
struct world_pickle_suite : boost::python::pickle_suite struct world_pickle_suite : boost::python::pickle_suite
{ {
static static
@@ -144,76 +161,92 @@
} }
}; };
</pre> </pre>
</li> <li>2. Establishing the Python bindings for the entire suite:
<pre>
<li>2. Establishing the Python bindings for the entire suite:
<pre>
class_&lt;world&gt;("world", args&lt;const std::string&amp;&gt;()) class_&lt;world&gt;("world", args&lt;const std::string&amp;&gt;())
// ... // ...
.def_pickle(world_pickle_suite()) .def_pickle(world_pickle_suite())
// ... // ...
</pre> </pre>
</li> </ul>
</ul>
<p>For simplicity, the <tt>__dict__</tt> is not included in the result of <p>
<tt>__getstate__</tt>. This is not generally recommended, but a valid For simplicity, the <tt>__dict__</tt> is not included in the result
approach if it is anticipated that the object's <tt>__dict__</tt> will of <tt>__getstate__</tt>. This is not generally recommended, but a
always be empty. Note that the safety guard described below will catch valid approach if it is anticipated that the object's
the cases where this assumption is violated.</p> <tt>__dict__</tt> will always be empty. Note that the safety guard
<hr /> described below will catch the cases where this assumption is violated.
<h3><a href="../../test/pickle3.cpp"><tt>pickle3.cpp</tt></a></h3>This <hr>
example is similar to <a href= <h3><a href="../../test/pickle3.cpp"><tt>pickle3.cpp</tt></a></h3>
"../../test/pickle2.cpp"><tt>pickle2.cpp</tt></a>. However, the object's
<tt>__dict__</tt> is included in the result of <tt>__getstate__</tt>.
This requires a little more code but is unavoidable if the object's
<tt>__dict__</tt> is not always empty.
<hr />
<h2>Pitfall and Safety Guard</h2>The pickle protocol described above has This example is similar to <a
an important pitfall that the end user of a Boost.Python extension module href="../../test/pickle2.cpp"><tt>pickle2.cpp</tt></a>. However, the
might not be aware of: object's <tt>__dict__</tt> is included in the result of
<tt>__getstate__</tt>. This requires a little more code but is
unavoidable if the object's <tt>__dict__</tt> is not always empty.
<p><strong><tt>__getstate__</tt> is defined and the instance's <hr>
<tt>__dict__</tt> is not empty.</strong></p> <h2>Pitfall and Safety Guard</h2>
<p>The author of a Boost.Python extension class might provide a The pickle protocol described above has an important pitfall that the
<tt>__getstate__</tt> method without considering the possibilities end user of a Boost.Python extension module might not be aware of:
that:</p> <p>
<strong>
<tt>__getstate__</tt> is defined and the instance's <tt>__dict__</tt>
is not empty.
</strong>
<p>
<ul> The author of a Boost.Python extension class might provide a
<li>his class is used in Python as a base class. Most likely the <tt>__getstate__</tt> method without considering the possibilities
<tt>__dict__</tt> of instances of the derived class needs to be pickled that:
in order to restore the instances correctly.</li>
<li>the user adds items to the instance's <tt>__dict__</tt> directly. <p>
Again, the <tt>__dict__</tt> of the instance then needs to be <ul>
pickled.</li> <li>
</ul> his class is used in Python as a base class. Most likely the
<tt>__dict__</tt> of instances of the derived class needs to be
pickled in order to restore the instances correctly.
<p>To alert the user to this highly unobvious problem, a safety guard is <p>
provided. If <tt>__getstate__</tt> is defined and the instance's <li>
<tt>__dict__</tt> is not empty, Boost.Python tests if the class has an the user adds items to the instance's <tt>__dict__</tt> directly.
attribute <tt>__getstate_manages_dict__</tt>. An exception is raised if Again, the <tt>__dict__</tt> of the instance then needs to be
this attribute is not defined:</p> pickled.
<pre>
</ul>
<p>
To alert the user to this highly unobvious problem, a safety guard is
provided. If <tt>__getstate__</tt> is defined and the instance's
<tt>__dict__</tt> is not empty, Boost.Python tests if the class has
an attribute <tt>__getstate_manages_dict__</tt>. An exception is
raised if this attribute is not defined:
<pre>
RuntimeError: Incomplete pickle support (__getstate_manages_dict__ not set) RuntimeError: Incomplete pickle support (__getstate_manages_dict__ not set)
</pre>To resolve this problem, it should first be established that the <tt> </pre>
__getstate__</tt> and <tt>__setstate__</tt> methods manage the
instances's <tt>__dict__</tt> correctly. Note that this can be done To resolve this problem, it should first be established that the
either at the C++ or the Python level. Finally, the safety guard should <tt>__getstate__</tt> and <tt>__setstate__</tt> methods manage the
intentionally be overridden. E.g. in C++ (from <a href= instances's <tt>__dict__</tt> correctly. Note that this can be done
"../../test/pickle3.cpp"><tt>pickle3.cpp</tt></a>): either at the C++ or the Python level. Finally, the safety guard
<pre> should intentionally be overridden. E.g. in C++ (from
<a href="../../test/pickle3.cpp"><tt>pickle3.cpp</tt></a>):
<pre>
struct world_pickle_suite : boost::python::pickle_suite struct world_pickle_suite : boost::python::pickle_suite
{ {
// ... // ...
static bool getstate_manages_dict() { return true; } static bool getstate_manages_dict() { return true; }
}; };
</pre>Alternatively in Python: </pre>
<pre>
Alternatively in Python:
<pre>
import your_bpl_module import your_bpl_module
class your_class(your_bpl_module.your_class): class your_class(your_bpl_module.your_class):
__getstate_manages_dict__ = 1 __getstate_manages_dict__ = 1
@@ -222,41 +255,54 @@
def __setstate__(self, state): def __setstate__(self, state):
# your code here # your code here
</pre> </pre>
<hr />
<h2>Practical Advice</h2> <hr>
<h2>Practical Advice</h2>
<ul> <ul>
<li>In Boost.Python extension modules with many extension classes, <li>
providing complete pickle support for all classes would be a In Boost.Python extension modules with many extension classes,
significant overhead. In general complete pickle support should only be providing complete pickle support for all classes would be a
implemented for extension classes that will eventually be pickled.</li> significant overhead. In general complete pickle support should
only be implemented for extension classes that will eventually
be pickled.
<li>Avoid using <tt>__getstate__</tt> if the instance can also be <p>
reconstructed by way of <tt>__getinitargs__</tt>. This automatically <li>
avoids the pitfall described above.</li> Avoid using <tt>__getstate__</tt> if the instance can also be
reconstructed by way of <tt>__getinitargs__</tt>. This automatically
avoids the pitfall described above.
<li>If <tt>__getstate__</tt> is required, include the instance's <p>
<tt>__dict__</tt> in the Python object that is returned.</li> <li>
</ul> If <tt>__getstate__</tt> is required, include the instance's
<hr /> <tt>__dict__</tt> in the Python object that is returned.
<h2>Light-weight alternative: pickle support implemented in Python</h2> </ul>
<h3><a href="../../test/pickle4.cpp"><tt>pickle4.cpp</tt></a></h3>The <hr>
<tt>pickle4.cpp</tt> example demonstrates an alternative technique for <h2>Light-weight alternative: pickle support implemented in Python</h2>
implementing pickle support. First we direct Boost.Python via the
<tt>class_::enable_pickling()</tt> member function to define only the <h3><a href="../../test/pickle4.cpp"><tt>pickle4.cpp</tt></a></h3>
basic attributes required for pickling:
<pre> The <tt>pickle4.cpp</tt> example demonstrates an alternative technique
for implementing pickle support. First we direct Boost.Python via
the <tt>class_::enable_pickling()</tt> member function to define only
the basic attributes required for pickling:
<pre>
class_&lt;world&gt;("world", args&lt;const std::string&amp;&gt;()) class_&lt;world&gt;("world", args&lt;const std::string&amp;&gt;())
// ... // ...
.enable_pickling() .enable_pickling()
// ... // ...
</pre>This enables the standard Python pickle interface as described in the </pre>
Python documentation. By "injecting" a <tt>__getinitargs__</tt> method into
the definition of the wrapped class we make all instances pickleable: This enables the standard Python pickle interface as described
<pre> in the Python documentation. By &quot;injecting&quot; a
<tt>__getinitargs__</tt> method into the definition of the wrapped
class we make all instances pickleable:
<pre>
# import the wrapped world class # import the wrapped world class
from pickle4_ext import world from pickle4_ext import world
@@ -266,15 +312,18 @@ the definition of the wrapped class we make all instances pickleable:
# now inject __getinitargs__ (Python is a dynamic language!) # now inject __getinitargs__ (Python is a dynamic language!)
world.__getinitargs__ = world_getinitargs world.__getinitargs__ = world_getinitargs
</pre>See also the <a href= </pre>
"../tutorial/doc/html/python/techniques.html#python.extending_wrapped_objects_in_python">
tutorial section</a> on injecting additional methods from Python.
<hr />
© Copyright Ralf W. Grosse-Kunstleve 2001-2004. Distributed under the
Boost Software License, Version 1.0. (See accompanying file
LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
<p>Updated: Feb 2004.</p> See also the
</div> <a href="../tutorial/doc/html/python/techniques.html#python.extending_wrapped_objects_in_python"
</body> >tutorial section</a> on injecting additional methods from Python.
</html>
<hr>
&copy; Copyright Ralf W. Grosse-Kunstleve 2001-2004. Distributed under
the Boost Software License, Version 1.0. (See accompanying file
LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
<p>
Updated: Feb 2004.
</div>

0
doc/v2/raw_function.html Executable file → Normal file
View File

0
doc/v2/return_arg.html Executable file → Normal file
View File

View File

@@ -167,13 +167,12 @@ PyObject* postcall(PyObject* args, PyObject* result);
class Bar class Bar
{ {
public:
Bar(int x) : x(x) {} Bar(int x) : x(x) {}
int get_x() const { return x; } int get_x() const { return x; }
void set_x(int x) { this-&gt;x = x; } void set_x(int x) { this-&gt;x = x; }
private: private:
int x; int x;
}; }
class Foo class Foo
{ {
@@ -190,7 +189,7 @@ class Foo
using namespace boost::python; using namespace boost::python;
BOOST_PYTHON_MODULE(internal_refs) BOOST_PYTHON_MODULE(internal_refs)
{ {
class_&lt;Bar&gt;("Bar", init&lt;int&gt;()) class_&lt;Bar&gt;("Bar")
.def("get_x", &amp;Bar::get_x) .def("get_x", &amp;Bar::get_x)
.def("set_x", &amp;Bar::set_x) .def("set_x", &amp;Bar::set_x)
; ;

View File

@@ -85,7 +85,7 @@ namespace boost { namespace python
object stop(); object stop();
object step(); object step();
// The return type of slice::get_indices() // The return type of slice::get_indicies()
template &lt;typename RandomAccessIterator&gt; template &lt;typename RandomAccessIterator&gt;
struct range struct range
{ {
@@ -96,7 +96,7 @@ namespace boost { namespace python
template &lt;typename RandomAccessIterator&gt; template &lt;typename RandomAccessIterator&gt;
range&lt;RandomAccessIterator&gt; range&lt;RandomAccessIterator&gt;
get_indices( get_indicies(
RandomAccessIterator const&amp; begin, RandomAccessIterator const&amp; begin,
RandomAccessIterator const&amp; end); RandomAccessIterator const&amp; end);
}; };
@@ -164,7 +164,7 @@ slice object, but in practice they are usually integers.</dt>
<pre> <pre>
template &lt;typename RandomAccessIterator&gt; template &lt;typename RandomAccessIterator&gt;
slice::range&lt;RandomAccessIterator&gt; slice::range&lt;RandomAccessIterator&gt;
slice::get_indices( slice::get_indicies(
RandomAccessIterator const&amp; begin, RandomAccessIterator const&amp; begin,
RandomAccessIterator const&amp; end) const; RandomAccessIterator const&amp; end) const;
</pre> </pre>
@@ -173,8 +173,8 @@ slice::get_indices(
Iterators that form a half-open range.</dt> Iterators that form a half-open range.</dt>
<dt><b>Effects:</b> Create a RandomAccessIterator pair that defines a <dt><b>Effects:</b> Create a RandomAccessIterator pair that defines a
fully-closed range within the [begin,end) range of its arguments.&nbsp; fully-closed range within the [begin,end) range of its arguments.&nbsp;
This function translates this slice's indices while accounting for the This function translates this slice's indicies while accounting for the
effects of any PyNone or negative indices, and non-singular step sizes.</dt> effects of any PyNone or negative indicies, and non-singular step sizes.</dt>
<dt><b>Returns:</b> a slice::range <dt><b>Returns:</b> a slice::range
that has been initialized with a non-zero value of step and a pair of that has been initialized with a non-zero value of step and a pair of
RandomAccessIterators that point within the range of this functions RandomAccessIterators that point within the range of this functions
@@ -182,7 +182,7 @@ arguments and define a closed interval.</dt>
<dt><b>Throws:</b> <a href="definitions.html#raise">Raises</a> a Python <code>TypeError</code> exception if any of this slice's arguments <dt><b>Throws:</b> <a href="definitions.html#raise">Raises</a> a Python <code>TypeError</code> exception if any of this slice's arguments
are neither references to <code>PyNone</code> nor convertible to <code>int</code>.&nbsp; Throws are neither references to <code>PyNone</code> nor convertible to <code>int</code>.&nbsp; Throws
<code>std::invalid_argument</code> if the resulting range would be empty.&nbsp; You <code>std::invalid_argument</code> if the resulting range would be empty.&nbsp; You
should always wrap calls to <code>slice::get_indices()</code> should always wrap calls to <code>slice::get_indicies()</code>
within <code>try { ...; } catch (std::invalid_argument) {}</code> to within <code>try { ...; } catch (std::invalid_argument) {}</code> to
handle this case and take appropriate action.</dt> handle this case and take appropriate action.</dt>
<dt><b>Rationale</b>: closed-interval: If <dt><b>Rationale</b>: closed-interval: If
@@ -221,7 +221,7 @@ double partial_sum(std::vector&lt;double&gt; const&amp; Foo, const slice index)
{ {
slice::range&lt;std::vector&lt;double&gt;::const_iterator&gt; bounds; slice::range&lt;std::vector&lt;double&gt;::const_iterator&gt; bounds;
try { try {
bounds = index.get_indices&lt;&gt;(Foo.begin(), Foo.end()); bounds = index.get_indicies&lt;&gt;(Foo.begin(), Foo.end());
} }
catch (std::invalid_argument) { catch (std::invalid_argument) {
return 0.0; return 0.0;

0
doc/v2/stl_iterator.html Executable file → Normal file
View File

0
doc/v2/type_id.html Executable file → Normal file
View File

View File

@@ -91,7 +91,7 @@
<hr> <hr>
<h2> <h2>
<a name="introduction">Introduction</a> <a name="introduction">Introduction</a>
</h2>This header provides facilities for establishing a lifetime </h2>This header provides faciliites for establishing a lifetime
dependency between two of a function's Python argument or result objects. dependency between two of a function's Python argument or result objects.
The <i>ward</i> object will not be destroyed until after the custodian as The <i>ward</i> object will not be destroyed until after the custodian as
long as the <i>custodian</i> object supports <a href= long as the <i>custodian</i> object supports <a href=

0
doc/v2/wrapper.html Executable file → Normal file
View File

View File

@@ -11,10 +11,7 @@ use-project boost
# boost_python library from the project whose global ID is # boost_python library from the project whose global ID is
# /boost/python. # /boost/python.
project project
: requirements <library>/boost/python//boost_python : requirements <library>/boost/python//boost_python ;
<implicit-dependency>/boost//headers
: usage-requirements <implicit-dependency>/boost//headers
;
# Declare the three extension modules. You can specify multiple # Declare the three extension modules. You can specify multiple
# source files after the colon separated by spaces. # source files after the colon separated by spaces.

0
example/boost-build.jam Executable file → Normal file
View File

View File

@@ -12,8 +12,6 @@ use-project boost
# /boost/python. # /boost/python.
project boost-python-quickstart project boost-python-quickstart
: requirements <library>/boost/python//boost_python : requirements <library>/boost/python//boost_python
<implicit-dependency>/boost//headers
: usage-requirements <implicit-dependency>/boost//headers
; ;
# Make the definition of the python-extension rule available # Make the definition of the python-extension rule available

View File

@@ -2,15 +2,6 @@
# Software License, Version 1.0. (See accompanying # Software License, Version 1.0. (See accompanying
# file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) # file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
import python ;
if ! [ python.configured ]
{
ECHO "notice: no Python configured in user-config.jam" ;
ECHO "notice: will use default configuration" ;
using python ;
}
# Specify the path to the Boost project. If you move this project, # Specify the path to the Boost project. If you move this project,
# adjust this path to refer to the Boost root directory. # adjust this path to refer to the Boost root directory.
use-project boost use-project boost
@@ -20,23 +11,12 @@ use-project boost
# boost_python library from the project whose global ID is # boost_python library from the project whose global ID is
# /boost/python. # /boost/python.
project project
: requirements <library>/boost/python//boost_python : requirements <library>/boost/python//boost_python ;
<implicit-dependency>/boost//headers
: usage-requirements <implicit-dependency>/boost//headers
;
# Declare the three extension modules. You can specify multiple # Declare the three extension modules. You can specify multiple
# source files after the colon separated by spaces. # source files after the colon separated by spaces.
python-extension hello_ext : hello.cpp ; python-extension hello_ext : hello.cpp ;
# Put the extension and Boost.Python DLL in the current directory, so
# that running script by hand works.
install convenient_copy
: hello_ext
: <install-dependencies>on <install-type>SHARED_LIB <install-type>PYTHON_EXTENSION
<location>.
;
# A little "rule" (function) to clean up the syntax of declaring tests # A little "rule" (function) to clean up the syntax of declaring tests
# of these extension modules. # of these extension modules.
local rule run-test ( test-name : sources + ) local rule run-test ( test-name : sources + )

0
include/boost/python/arg_from_python.hpp Executable file → Normal file
View File

0
include/boost/python/base_type_traits.hpp Executable file → Normal file
View File

0
include/boost/python/borrowed.hpp Executable file → Normal file
View File

View File

@@ -38,10 +38,7 @@ namespace boost { namespace python {
# endif // CALL_DWA2002411_HPP # endif // CALL_DWA2002411_HPP
// For gcc 4.4 compatability, we must include the #elif BOOST_PP_ITERATION_DEPTH() == 1
// BOOST_PP_ITERATION_DEPTH test inside an #else clause.
#else // BOOST_PP_IS_ITERATING
#if BOOST_PP_ITERATION_DEPTH() == 1
# if !(BOOST_WORKAROUND(__MWERKS__, > 0x3100) \ # if !(BOOST_WORKAROUND(__MWERKS__, > 0x3100) \
&& BOOST_WORKAROUND(__MWERKS__, BOOST_TESTED_AT(0x3201))) && BOOST_WORKAROUND(__MWERKS__, BOOST_TESTED_AT(0x3201)))
# line BOOST_PP_LINE(__LINE__, call.hpp) # line BOOST_PP_LINE(__LINE__, call.hpp)
@@ -79,5 +76,4 @@ call(PyObject* callable
# undef N # undef N
#endif // BOOST_PP_ITERATION_DEPTH()
#endif #endif

View File

@@ -37,10 +37,7 @@ namespace boost { namespace python {
# endif // CALL_METHOD_DWA2002411_HPP # endif // CALL_METHOD_DWA2002411_HPP
// For gcc 4.4 compatability, we must include the #elif BOOST_PP_ITERATION_DEPTH() == 1
// BOOST_PP_ITERATION_DEPTH test inside an #else clause.
#else // BOOST_PP_IS_ITERATING
#if BOOST_PP_ITERATION_DEPTH() == 1
# if !(BOOST_WORKAROUND(__MWERKS__, > 0x3100) \ # if !(BOOST_WORKAROUND(__MWERKS__, > 0x3100) \
&& BOOST_WORKAROUND(__MWERKS__, BOOST_TESTED_AT(0x3201))) && BOOST_WORKAROUND(__MWERKS__, BOOST_TESTED_AT(0x3201)))
# line BOOST_PP_LINE(__LINE__, call_method.hpp) # line BOOST_PP_LINE(__LINE__, call_method.hpp)
@@ -79,5 +76,4 @@ call_method(PyObject* self, char const* name
# undef N # undef N
#endif // BOOST_PP_ITERATION_DEPTH()
#endif // BOOST_PP_IS_ITERATING #endif // BOOST_PP_IS_ITERATING

0
include/boost/python/cast.hpp Executable file → Normal file
View File

View File

@@ -138,8 +138,7 @@ namespace detail
static void static void
must_be_derived_class_member(Default const&) must_be_derived_class_member(Default const&)
{ {
// https://svn.boost.org/trac/boost/ticket/5803 typedef typename assertion<mpl::not_<is_same<Default,Fn> > >::failed test0;
//typedef typename assertion<mpl::not_<is_same<Default,Fn> > >::failed test0;
# if !BOOST_WORKAROUND(__MWERKS__, <= 0x2407) # if !BOOST_WORKAROUND(__MWERKS__, <= 0x2407)
typedef typename assertion<is_polymorphic<T> >::failed test1; typedef typename assertion<is_polymorphic<T> >::failed test1;
# endif # endif

0
include/boost/python/converter/arg_from_python.hpp Executable file → Normal file
View File

0
include/boost/python/converter/arg_to_python.hpp Executable file → Normal file
View File

0
include/boost/python/converter/arg_to_python_base.hpp Executable file → Normal file
View File

View File

@@ -90,14 +90,6 @@ namespace detail
BOOST_PYTHON_ARG_TO_PYTHON_BY_VALUE(T,expr) BOOST_PYTHON_ARG_TO_PYTHON_BY_VALUE(T,expr)
// Specialize converters for signed and unsigned T to Python Int // Specialize converters for signed and unsigned T to Python Int
#if PY_VERSION_HEX >= 0x03000000
# define BOOST_PYTHON_TO_INT(T) \
BOOST_PYTHON_TO_PYTHON_BY_VALUE(signed T, ::PyLong_FromLong(x), &PyLong_Type) \
BOOST_PYTHON_TO_PYTHON_BY_VALUE(unsigned T, ::PyLong_FromUnsignedLong(x), &PyLong_Type)
#else
# define BOOST_PYTHON_TO_INT(T) \ # define BOOST_PYTHON_TO_INT(T) \
BOOST_PYTHON_TO_PYTHON_BY_VALUE(signed T, ::PyInt_FromLong(x), &PyInt_Type) \ BOOST_PYTHON_TO_PYTHON_BY_VALUE(signed T, ::PyInt_FromLong(x), &PyInt_Type) \
BOOST_PYTHON_TO_PYTHON_BY_VALUE( \ BOOST_PYTHON_TO_PYTHON_BY_VALUE( \
@@ -106,7 +98,6 @@ namespace detail
(std::numeric_limits<long>::max)()) \ (std::numeric_limits<long>::max)()) \
? ::PyLong_FromUnsignedLong(x) \ ? ::PyLong_FromUnsignedLong(x) \
: ::PyInt_FromLong(x), &PyInt_Type) : ::PyInt_FromLong(x), &PyInt_Type)
#endif
// Bool is not signed. // Bool is not signed.
#if PY_VERSION_HEX >= 0x02030000 #if PY_VERSION_HEX >= 0x02030000
@@ -122,48 +113,20 @@ BOOST_PYTHON_TO_INT(short)
BOOST_PYTHON_TO_INT(int) BOOST_PYTHON_TO_INT(int)
BOOST_PYTHON_TO_INT(long) BOOST_PYTHON_TO_INT(long)
# if defined(_MSC_VER) && defined(_WIN64) && PY_VERSION_HEX < 0x03000000 // using Python's macro instead of Boost's - we don't seem to get the
/* Under 64-bit Windows std::size_t is "unsigned long long". To avoid // config right all the time.
getting a Python long for each std::size_t the value is checked before # ifdef HAVE_LONG_LONG
the conversion. A std::size_t is converted to a simple Python int BOOST_PYTHON_TO_PYTHON_BY_VALUE(signed BOOST_PYTHON_LONG_LONG, ::PyLong_FromLongLong(x), &PyInt_Type)
if possible; a Python long appears only if the value is too small or BOOST_PYTHON_TO_PYTHON_BY_VALUE(unsigned BOOST_PYTHON_LONG_LONG, ::PyLong_FromUnsignedLongLong(x), &PyInt_Type)
too large to fit into a simple int. */
BOOST_PYTHON_TO_PYTHON_BY_VALUE(
signed BOOST_PYTHON_LONG_LONG,
( x < static_cast<signed BOOST_PYTHON_LONG_LONG>(
(std::numeric_limits<long>::min)())
|| x > static_cast<signed BOOST_PYTHON_LONG_LONG>(
(std::numeric_limits<long>::max)()))
? ::PyLong_FromLongLong(x)
: ::PyInt_FromLong(static_cast<long>(x)), &PyInt_Type)
BOOST_PYTHON_TO_PYTHON_BY_VALUE(
unsigned BOOST_PYTHON_LONG_LONG,
x > static_cast<unsigned BOOST_PYTHON_LONG_LONG>(
(std::numeric_limits<long>::max)())
? ::PyLong_FromUnsignedLongLong(x)
: ::PyInt_FromLong(static_cast<long>(x)), &PyInt_Type)
//
# elif defined(HAVE_LONG_LONG) // using Python's macro instead of Boost's
// - we don't seem to get the config right
// all the time.
BOOST_PYTHON_TO_PYTHON_BY_VALUE(signed BOOST_PYTHON_LONG_LONG, ::PyLong_FromLongLong(x), &PyLong_Type)
BOOST_PYTHON_TO_PYTHON_BY_VALUE(unsigned BOOST_PYTHON_LONG_LONG, ::PyLong_FromUnsignedLongLong(x), &PyLong_Type)
# endif # endif
# undef BOOST_TO_PYTHON_INT # undef BOOST_TO_PYTHON_INT
#if PY_VERSION_HEX >= 0x03000000
BOOST_PYTHON_TO_PYTHON_BY_VALUE(char, converter::do_return_to_python(x), &PyUnicode_Type)
BOOST_PYTHON_TO_PYTHON_BY_VALUE(char const*, converter::do_return_to_python(x), &PyUnicode_Type)
BOOST_PYTHON_TO_PYTHON_BY_VALUE(std::string, ::PyUnicode_FromStringAndSize(x.data(),implicit_cast<ssize_t>(x.size())), &PyUnicode_Type)
#else
BOOST_PYTHON_TO_PYTHON_BY_VALUE(char, converter::do_return_to_python(x), &PyString_Type) BOOST_PYTHON_TO_PYTHON_BY_VALUE(char, converter::do_return_to_python(x), &PyString_Type)
BOOST_PYTHON_TO_PYTHON_BY_VALUE(char const*, converter::do_return_to_python(x), &PyString_Type) BOOST_PYTHON_TO_PYTHON_BY_VALUE(char const*, converter::do_return_to_python(x), &PyString_Type)
BOOST_PYTHON_TO_PYTHON_BY_VALUE(std::string, ::PyString_FromStringAndSize(x.data(),implicit_cast<ssize_t>(x.size())), &PyString_Type) BOOST_PYTHON_TO_PYTHON_BY_VALUE(std::string, ::PyString_FromStringAndSize(x.data(),implicit_cast<ssize_t>(x.size())), &PyString_Type)
#endif
#if defined(Py_USING_UNICODE) && !defined(BOOST_NO_STD_WSTRING) #if defined(Py_USING_UNICODE) && !defined(BOOST_NO_STD_WSTRING)
BOOST_PYTHON_TO_PYTHON_BY_VALUE(std::wstring, ::PyUnicode_FromWideChar(x.data(),implicit_cast<ssize_t>(x.size())), &PyUnicode_Type) BOOST_PYTHON_TO_PYTHON_BY_VALUE(std::wstring, ::PyUnicode_FromWideChar(x.data(),implicit_cast<ssize_t>(x.size())), &PyString_Type)
# endif # endif
BOOST_PYTHON_TO_PYTHON_BY_VALUE(float, ::PyFloat_FromDouble(x), &PyFloat_Type) BOOST_PYTHON_TO_PYTHON_BY_VALUE(float, ::PyFloat_FromDouble(x), &PyFloat_Type)
BOOST_PYTHON_TO_PYTHON_BY_VALUE(double, ::PyFloat_FromDouble(x), &PyFloat_Type) BOOST_PYTHON_TO_PYTHON_BY_VALUE(double, ::PyFloat_FromDouble(x), &PyFloat_Type)

View File

0
include/boost/python/converter/object_manager.hpp Executable file → Normal file
View File

View File

@@ -34,9 +34,7 @@ struct pyobject_traits<PyObject>
// This is not an exhaustive list; should be expanded. // This is not an exhaustive list; should be expanded.
BOOST_PYTHON_BUILTIN_OBJECT_TRAITS(Type); BOOST_PYTHON_BUILTIN_OBJECT_TRAITS(Type);
BOOST_PYTHON_BUILTIN_OBJECT_TRAITS(List); BOOST_PYTHON_BUILTIN_OBJECT_TRAITS(List);
#if PY_VERSION_HEX < 0x03000000
BOOST_PYTHON_BUILTIN_OBJECT_TRAITS(Int); BOOST_PYTHON_BUILTIN_OBJECT_TRAITS(Int);
#endif
BOOST_PYTHON_BUILTIN_OBJECT_TRAITS(Long); BOOST_PYTHON_BUILTIN_OBJECT_TRAITS(Long);
BOOST_PYTHON_BUILTIN_OBJECT_TRAITS(Dict); BOOST_PYTHON_BUILTIN_OBJECT_TRAITS(Dict);
BOOST_PYTHON_BUILTIN_OBJECT_TRAITS(Tuple); BOOST_PYTHON_BUILTIN_OBJECT_TRAITS(Tuple);

0
include/boost/python/converter/pytype_function.hpp Executable file → Normal file
View File

View File

@@ -30,7 +30,7 @@ namespace registry
BOOST_PYTHON_DECL void insert(to_python_function_t, type_info, PyTypeObject const* (*to_python_target_type)() = 0); BOOST_PYTHON_DECL void insert(to_python_function_t, type_info, PyTypeObject const* (*to_python_target_type)() = 0);
// Insert an lvalue from_python converter // Insert an lvalue from_python converter
BOOST_PYTHON_DECL void insert(convertible_function, type_info, PyTypeObject const* (*expected_pytype)() = 0); BOOST_PYTHON_DECL void insert(void* (*convert)(PyObject*), type_info, PyTypeObject const* (*expected_pytype)() = 0);
// Insert an rvalue from_python converter // Insert an rvalue from_python converter
BOOST_PYTHON_DECL void insert( BOOST_PYTHON_DECL void insert(

0
include/boost/python/converter/return_from_python.hpp Executable file → Normal file
View File

View File

@@ -45,14 +45,10 @@ struct shared_ptr_from_python
if (data->convertible == source) if (data->convertible == source)
new (storage) shared_ptr<T>(); new (storage) shared_ptr<T>();
else else
{
boost::shared_ptr<void> hold_convertible_ref_count(
(void*)0, shared_ptr_deleter(handle<>(borrowed(source))) );
// use aliasing constructor
new (storage) shared_ptr<T>( new (storage) shared_ptr<T>(
hold_convertible_ref_count, static_cast<T*>(data->convertible),
static_cast<T*>(data->convertible)); shared_ptr_deleter(handle<>(borrowed(source)))
} );
data->convertible = storage; data->convertible = storage;
} }

0
include/boost/python/def_visitor.hpp Executable file → Normal file
View File

0
include/boost/python/detail/borrowed_ptr.hpp Executable file → Normal file
View File

View File

@@ -76,13 +76,13 @@
# if BOOST_PYTHON_USE_GCC_SYMBOL_VISIBILITY # if BOOST_PYTHON_USE_GCC_SYMBOL_VISIBILITY
# if defined(BOOST_PYTHON_SOURCE) # if defined(BOOST_PYTHON_SOURCE)
# define BOOST_PYTHON_DECL __attribute__ ((__visibility__("default"))) # define BOOST_PYTHON_DECL __attribute__ ((visibility("default")))
# define BOOST_PYTHON_BUILD_DLL # define BOOST_PYTHON_BUILD_DLL
# else # else
# define BOOST_PYTHON_DECL # define BOOST_PYTHON_DECL
# endif # endif
# define BOOST_PYTHON_DECL_FORWARD # define BOOST_PYTHON_DECL_FORWARD
# define BOOST_PYTHON_DECL_EXCEPTION __attribute__ ((__visibility__("default"))) # define BOOST_PYTHON_DECL_EXCEPTION __attribute__ ((visibility("default")))
# elif (defined(_WIN32) || defined(__CYGWIN__)) # elif (defined(_WIN32) || defined(__CYGWIN__))
# if defined(BOOST_PYTHON_SOURCE) # if defined(BOOST_PYTHON_SOURCE)
# define BOOST_PYTHON_DECL __declspec(dllexport) # define BOOST_PYTHON_DECL __declspec(dllexport)

0
include/boost/python/detail/convertible.hpp Executable file → Normal file
View File

0
include/boost/python/detail/copy_ctor_mutates_rhs.hpp Executable file → Normal file
View File

View File

@@ -55,8 +55,8 @@ inline decorated_type_info::decorated_type_info(type_info base_t, decoration dec
inline bool decorated_type_info::operator<(decorated_type_info const& rhs) const inline bool decorated_type_info::operator<(decorated_type_info const& rhs) const
{ {
return m_decoration < rhs.m_decoration return m_decoration < rhs.m_decoration
|| (m_decoration == rhs.m_decoration || m_decoration == rhs.m_decoration
&& m_base_type < rhs.m_base_type); && m_base_type < rhs.m_base_type;
} }
inline bool decorated_type_info::operator==(decorated_type_info const& rhs) const inline bool decorated_type_info::operator==(decorated_type_info const& rhs) const

0
include/boost/python/detail/def_helper_fwd.hpp Executable file → Normal file
View File

View File

@@ -30,7 +30,7 @@ struct value_destroyer<
template <class T> template <class T>
static void execute(T const volatile* p) static void execute(T const volatile* p)
{ {
p->~T(); p->T::~T();
} }
}; };

0
include/boost/python/detail/enable_if.hpp Executable file → Normal file
View File

0
include/boost/python/detail/force_instantiate.hpp Executable file → Normal file
View File

0
include/boost/python/detail/is_shared_ptr.hpp Executable file → Normal file
View File

0
include/boost/python/detail/is_wrapper.hpp Executable file → Normal file
View File

View File

@@ -57,7 +57,7 @@ object make_keyword_range_constructor(
, Holder* = 0 , Holder* = 0
, ArgList* = 0, Arity* = 0) , ArgList* = 0, Arity* = 0)
{ {
#if !defined( BOOST_PYTHON_NO_PY_SIGNATURES) && defined( BOOST_PYTHON_PY_SIGNATURES_PROPER_INIT_SELF_TYPE) #if !defined( BOOST_PYTHON_NO_PY_SIGNATURES) && defined( BOOST_PYTHON_PY_SYGNATURES_PROPER_INIT_SELF_TYPE)
python_class<BOOST_DEDUCED_TYPENAME Holder::value_type>::register_(); python_class<BOOST_DEDUCED_TYPENAME Holder::value_type>::register_();
#endif #endif
return detail::make_keyword_range_function( return detail::make_keyword_range_function(

View File

View File

@@ -47,15 +47,8 @@ enum operator_id
op_ixor, op_ixor,
op_ior, op_ior,
op_complex, op_complex,
#if PY_VERSION_HEX >= 0x03000000
op_bool,
#else
op_nonzero, op_nonzero,
#endif
op_repr op_repr
#if PY_VERSION_HEX >= 0x03000000
,op_truediv
#endif
}; };
}}} // namespace boost::python::detail }}} // namespace boost::python::detail

0
include/boost/python/detail/prefix.hpp Executable file → Normal file
View File

0
include/boost/python/detail/python_type.hpp Executable file → Normal file
View File

View File

@@ -86,10 +86,7 @@ result(X const&, short = 0) { return 0; }
# endif // RESULT_DWA2002521_HPP # endif // RESULT_DWA2002521_HPP
/* --------------- function pointers --------------- */ /* --------------- function pointers --------------- */
// For gcc 4.4 compatability, we must include the #elif BOOST_PP_ITERATION_DEPTH() == 1 && BOOST_PP_ITERATION_FLAGS() == BOOST_PYTHON_FUNCTION_POINTER
// BOOST_PP_ITERATION_DEPTH test inside an #else clause.
#else // BOOST_PP_IS_ITERATING
#if BOOST_PP_ITERATION_DEPTH() == 1 && BOOST_PP_ITERATION_FLAGS() == BOOST_PYTHON_FUNCTION_POINTER
# if !(BOOST_WORKAROUND(__MWERKS__, > 0x3100) \ # if !(BOOST_WORKAROUND(__MWERKS__, > 0x3100) \
&& BOOST_WORKAROUND(__MWERKS__, BOOST_TESTED_AT(0x3201))) && BOOST_WORKAROUND(__MWERKS__, BOOST_TESTED_AT(0x3201)))
# line BOOST_PP_LINE(__LINE__, result.hpp(function pointers)) # line BOOST_PP_LINE(__LINE__, result.hpp(function pointers))
@@ -131,5 +128,4 @@ boost::type<R>* result(R (T::*)(BOOST_PP_ENUM_PARAMS_Z(1, N, A)) Q, int = 0)
# undef N # undef N
# undef Q # undef Q
#endif // BOOST_PP_ITERATION_DEPTH()
#endif #endif

0
include/boost/python/detail/sfinae.hpp Executable file → Normal file
View File

View File

@@ -37,10 +37,7 @@ T& (* target(R (T::*)) )() { return 0; }
# endif // TARGET_DWA2002521_HPP # endif // TARGET_DWA2002521_HPP
/* --------------- function pointers --------------- */ /* --------------- function pointers --------------- */
// For gcc 4.4 compatability, we must include the #elif BOOST_PP_ITERATION_DEPTH() == 1 && BOOST_PP_ITERATION_FLAGS() == BOOST_PYTHON_FUNCTION_POINTER
// BOOST_PP_ITERATION_DEPTH test inside an #else clause.
#else // BOOST_PP_IS_ITERATING
#if BOOST_PP_ITERATION_DEPTH() == 1 && BOOST_PP_ITERATION_FLAGS() == BOOST_PYTHON_FUNCTION_POINTER
# if !(BOOST_WORKAROUND(__MWERKS__, > 0x3100) \ # if !(BOOST_WORKAROUND(__MWERKS__, > 0x3100) \
&& BOOST_WORKAROUND(__MWERKS__, BOOST_TESTED_AT(0x3201))) && BOOST_WORKAROUND(__MWERKS__, BOOST_TESTED_AT(0x3201)))
# line BOOST_PP_LINE(__LINE__, target.hpp(function_pointers)) # line BOOST_PP_LINE(__LINE__, target.hpp(function_pointers))
@@ -82,5 +79,4 @@ T& (* target(R (T::*)(BOOST_PP_ENUM_PARAMS_Z(1, N, A)) Q) )()
# undef N # undef N
# undef Q # undef Q
#endif // BOOST_PP_ITERATION_DEPTH()
#endif #endif

View File

@@ -2,15 +2,13 @@
// Distributed under the Boost Software License, Version 1.0. (See // Distributed under the Boost Software License, Version 1.0. (See
// accompanying file LICENSE_1_0.txt or copy at // accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt) // http://www.boost.org/LICENSE_1_0.txt)
#ifndef TRANSLATE_EXCEPTION_TDS20091020_HPP #ifndef TRANSLATE_EXCEPTION_DWA2002810_HPP
# define TRANSLATE_EXCEPTION_TDS20091020_HPP # define TRANSLATE_EXCEPTION_DWA2002810_HPP
# include <boost/python/detail/exception_handler.hpp> # include <boost/python/detail/exception_handler.hpp>
# include <boost/call_traits.hpp> # include <boost/call_traits.hpp>
# include <boost/type_traits/add_const.hpp> # include <boost/type_traits/add_const.hpp>
# include <boost/type_traits/add_reference.hpp>
# include <boost/type_traits/remove_reference.hpp>
# include <boost/function/function0.hpp> # include <boost/function/function0.hpp>

0
include/boost/python/detail/unwind_type.hpp Executable file → Normal file
View File

0
include/boost/python/detail/unwrap_type_id.hpp Executable file → Normal file
View File

0
include/boost/python/detail/unwrap_wrapper.hpp Executable file → Normal file
View File

0
include/boost/python/detail/value_arg.hpp Executable file → Normal file
View File

View File

@@ -175,19 +175,6 @@ typedef int pid_t;
( (op)->ob_type = (typeobj), _Py_NewReference((PyObject *)(op)), (op) ) ( (op)->ob_type = (typeobj), _Py_NewReference((PyObject *)(op)), (op) )
#endif #endif
// Define Python 3 macros for Python 2.x
#if PY_VERSION_HEX < 0x02060000
# define Py_TYPE(o) (((PyObject*)(o))->ob_type)
# define Py_REFCNT(o) (((PyObject*)(o))->ob_refcnt)
# define Py_SIZE(o) (((PyVarObject*)(o))->ob_size)
# define PyVarObject_HEAD_INIT(type, size) \
PyObject_HEAD_INIT(type) size,
#endif
#ifdef __MWERKS__ #ifdef __MWERKS__
# pragma warn_possunwant off # pragma warn_possunwant off
#elif _MSC_VER #elif _MSC_VER

0
include/boost/python/detail/wrapper_base.hpp Executable file → Normal file
View File

0
include/boost/python/docstring_options.hpp Executable file → Normal file
View File

View File

@@ -41,7 +41,7 @@ inline enum_<T>::enum_(char const* name, char const* doc )
, &enum_<T>::convertible_from_python , &enum_<T>::convertible_from_python
, &enum_<T>::construct , &enum_<T>::construct
, type_id<T>() , type_id<T>()
, doc , doc
) )
{ {
} }
@@ -79,11 +79,7 @@ void* enum_<T>::convertible_from_python(PyObject* obj)
template <class T> template <class T>
void enum_<T>::construct(PyObject* obj, converter::rvalue_from_python_stage1_data* data) void enum_<T>::construct(PyObject* obj, converter::rvalue_from_python_stage1_data* data)
{ {
#if PY_VERSION_HEX >= 0x03000000
T x = static_cast<T>(PyLong_AS_LONG(obj));
#else
T x = static_cast<T>(PyInt_AS_LONG(obj)); T x = static_cast<T>(PyInt_AS_LONG(obj));
#endif
void* const storage = ((converter::rvalue_from_python_storage<T>*)data)->storage.bytes; void* const storage = ((converter::rvalue_from_python_storage<T>*)data)->storage.bytes;
new (storage) T(x); new (storage) T(x);
data->convertible = storage; data->convertible = storage;

Some files were not shown because too many files have changed in this diff Show More