@@ -20,6 +20,8 @@ Available types include :class:`handle`, :class:`object`, :class:`bool_`,
20
20
Be sure to review the :ref: `pytypes_gotchas ` before using this heavily in
21
21
your C++ API.
22
22
23
+ .. _casting_back_and_forth :
24
+
23
25
Casting back and forth
24
26
======================
25
27
@@ -62,6 +64,7 @@ This example obtains a reference to the Python ``Decimal`` class.
62
64
py::object scipy = py::module::import("scipy");
63
65
return scipy.attr("__version__");
64
66
67
+
65
68
.. _calling_python_functions :
66
69
67
70
Calling Python functions
@@ -176,6 +179,47 @@ Generalized unpacking according to PEP448_ is also supported:
176
179
177
180
.. _PEP448 : https://www.python.org/dev/peps/pep-0448/
178
181
182
+ .. _implicit_casting :
183
+
184
+ Implicit casting
185
+ ================
186
+
187
+ When using the C++ interface for Python types, or calling Python functions,
188
+ objects of type :class: `object ` are returned. It is possible to invoke implicit
189
+ conversions to subclasses like :class: `dict `. The same holds for the proxy objects
190
+ returned by ``operator[] `` or ``obj.attr() ``.
191
+ Casting to subtypes improves code readability and allows values to be passed to
192
+ C++ functions that require a specific subtype rather than a generic :class: `object `.
193
+
194
+ .. code-block :: cpp
195
+
196
+ #include <pybind11/numpy.h>
197
+ using namespace pybind11::literals;
198
+
199
+ py::module os = py::module::import("os");
200
+ py::module path = py::module::import("os.path"); // like 'import os.path as path'
201
+ py::module np = py::module::import("numpy"); // like 'import numpy as np'
202
+
203
+ py::str curdir_abs = path.attr("abspath")(path.attr("curdir"));
204
+ py::print(py::str("Current directory: ") + curdir_abs);
205
+ py::dict environ = os.attr("environ");
206
+ py::print(environ["HOME"]);
207
+ py::array_t<float> arr = np.attr("ones")(3, "dtype"_a="float32");
208
+ py::print(py::repr(arr + py::int_(1)));
209
+
210
+ These implicit conversions are available for subclasses of :class: `object `; there
211
+ is no need to call ``obj.cast() `` explicitly as for custom classes, see
212
+ :ref: `casting_back_and_forth `.
213
+
214
+ .. note ::
215
+ If a trivial conversion via move constructor is not possible, both implicit and
216
+ explicit casting (calling ``obj.cast() ``) will attempt a "rich" conversion.
217
+ For instance, ``py::list env = os.attr("environ"); `` will succeed and is
218
+ equivalent to the Python code ``env = list(os.environ) `` that produces a
219
+ list of the dict keys.
220
+
221
+ .. TODO: Adapt text once PR #2349 has landed
222
+
179
223
Handling exceptions
180
224
===================
181
225
0 commit comments