1[section boost/python/lvalue_from_pytype.hpp] 2[section Introduction] 3<boost/python/lvalue_from_pytype.hpp> supplies a facility for extracting C++ objects from within Python instances of a given type. This is typically useful for dealing with "traditional" Python extension types. 4[endsect] 5[section Class template `lvalue_from_pytype`] 6Class template lvalue_from_pytype will register from_python converters which, given an object of the given Python type, can extract references and pointers to a particular C++ type. Its template arguments are: 7 8 In the table below, x denotes an object of type PythonObject& 9[table 10[[Parameter][Requirements][Semantics]] 11[[Extractor][a model of [link concepts.extractor `Extractor`] whose execute function returns a reference type.][Extracts the lvalue from the Python object once its type has been confirmed]] 12[[python_type][A compile-time constant [@http://www.python.org/doc/2.2/ext/dnt-type-methods.html `PyTypeObject*`]][The Python type of instances convertible by this converter. Python subtypes are also convertible.]] 13] 14`` 15namespace boost { namespace python 16{ 17 template <class Extractor, PyTypeObject const* python_type> 18 struct lvalue_from_pytype 19 { 20 lvalue_from_pytype(); 21 }; 22}} 23`` 24[section Class template `lvalue_from_pytype` constructor] 25``lvalue_from_pytype();`` 26[variablelist 27[[Effects][Registers converters which can convert Python objects of the given type to lvalues of the type returned by Extractor::execute.]] 28] 29[endsect] 30[endsect] 31[section Class template `extract_identity`] 32extract_identity is a model of [link concepts.extractor `Extractor`] which can be used in the common case where the C++ type to be extracted is the same as the Python object type. 33`` 34namespace boost { namespace python 35{ 36 template <class InstanceType> 37 struct extract_identity 38 { 39 static InstanceType& execute(InstanceType& c); 40 }; 41}} 42`` 43[section Class template `extract_identity` static functions] 44``InstanceType& execute(InstanceType& c);`` 45[variablelist 46[[Returns][c]] 47] 48[endsect] 49[endsect] 50[section Class template `extract_member`] 51`extract_member` is a model of [link concepts.extractor `Extractor`] which can be used in the common case in the common case where the C++ type to be extracted is a member of the Python object. 52`` 53namespace boost { namespace python 54{ 55 template <class InstanceType, class MemberType, MemberType (InstanceType::*member)> 56 struct extract_member 57 { 58 static MemberType& execute(InstanceType& c); 59 }; 60}} 61`` 62[section Class template `extract_member` static functions] 63``static MemberType& execute(InstanceType& c);`` 64[variablelist 65[[Returns][`c.*member`]] 66] 67[endsect] 68[endsect] 69[section Example] 70This example presumes that someone has implemented the standard noddy example module from the Python documentation, and we want to build a module which manipulates Noddys. Since noddy_NoddyObject is so simple that it carries no interesting information, the example is a bit contrived: it assumes you want to keep track of one particular object for some reason. This module would have to be dynamically linked to the module which defines noddy_NoddyType. 71 72In C++: 73`` 74#include <boost/python/module.hpp> 75#include <boost/python/handle.hpp> 76#include <boost/python/borrowed.hpp> 77#include <boost/python/lvalue_from_pytype.hpp> 78 79// definition lifted from the Python docs 80typedef struct { 81 PyObject_HEAD 82} noddy_NoddyObject; 83 84using namespace boost::python; 85static handle<noddy_NoddyObject> cache; 86 87bool is_cached(noddy_NoddyObject* x) 88{ 89 return x == cache.get(); 90} 91 92void set_cache(noddy_NoddyObject* x) 93{ 94 cache = handle<noddy_NoddyObject>(borrowed(x)); 95} 96 97BOOST_PYTHON_MODULE(noddy_cache) 98{ 99 def("is_cached", is_cached); 100 def("set_cache", set_cache); 101 102 // register Noddy lvalue converter 103 lvalue_from_pytype<extract_identity<noddy_NoddyObject>,&noddy_NoddyType>(); 104} 105`` 106In Python: 107`` 108>>> import noddy 109>>> n = noddy.new_noddy() 110>>> import noddy_cache 111>>> noddy_cache.is_cached(n) 1120 113>>> noddy_cache.set_cache(n) 114>>> noddy_cache.is_cached(n) 1151 116>>> noddy_cache.is_cached(noddy.new_noddy()) 1170 118`` 119[endsect] 120[endsect] 121