importing std::vector into python using pybind11 gives python error - pybind11

I'm trying to use pybind11's stl_bind header to no avail. I tried this:
#include <vector>
#include <pybind11/pybind11.h>
#include <pybind11/stl.h>
#include <pybind11/stl_bind.h>
namespace py = pybind11;
PYBIND11_PLUGIN(test)
{
py::module m("test", "pybind11 example plugin");
py::bind_vector<std::vector<double>>(m, "std_vector");
}
But when I try to use "std_vector" in python I get this:
In [1]: import test as b
In [2]: vec = b.std_vector()
---------------------------------------------------------------------------
ValueError Traceback (most recent call last)
<ipython-input-2-f81a62984a4e> in <module>()
----> 1 vec = b.std_vector()
ValueError: vector::reserve
Is this a bug, or am I using pybind11 wrong?

Aren't you missing a call to the PYBIND11_MAKE_OPAQUE macro before PYBIND11_PLUGIN(test)?
PYBIND11_MAKE_OPAQUE(std::vector<double>);
According to the PyBind11 doc you shoud first disable the defalut type conversion from vector to list.

Related

How to inherit from `LeafSystem<T>` in other pybind11 module

first of all, thanks for this great project!
I have the following situation: I'm developing a C++ library which uses drake as a dependency. Specifically I have a custom System, inheriting from LeafSystem<T>:
// my_system.h
#include <drake/systems/framework/leaf_system.h>
template <typename T>
class MySystem : public drake::systems::LeafSystem<T> {
public:
MySystem() {}
};
I want to expose this system also via a Python API, also using pybind11 like drake is doing, i.e.:
// my_module.cpp
#include "my_system.h"
#include <drake/systems/framework/leaf_system.h>
#include <pybind11/pybind11.h>
namespace py = pybind11;
PYBIND11_MODULE(my_module, m) {
py::module::import("pydrake.systems.framework");
py::class_<MySystem<double>, drake::systems::LeafSystem<double>>(m, "MySystem").def(py::init<>());
}
This compiles with CMake, life is good. But when I try to import MySystem in python, the base class cannot be resolved:
>>> import my_module
Traceback (most recent call last):
Cell In [2], line 1
import my_module
ImportError: generic_type: type "MySystem" referenced unknown base type "drake::systems::LeafSystem<double>"
I suspect it has something to do with the way drake generates the actual name of the binding, but this is all way beyond my head:
https://github.com/RobotLocomotion/drake/blob/72794d7818ef51629ed97faf6cd325004f49eb9a/bindings/pydrake/common/cpp_template_pybind.h#L90-L93
How can I create python bindings for my class which inherits from drake::system::framework::LeafSystem (or any other system, really)?
Thanks for your help!
The only relevant information I could find on pybind11 is from the officle docs about inheritance, which don't apply in my case, since the bindings of the base have already been written.
I tried to simulate the situation by compiling a libfoo.so which exports one base class Foo and its bindings. If MySystem inherits from Foo I can get the python binding to work just fine:
// Simulated foo library and its bindings
class Foo {};
#include "foo.h"
#include <pybind11/pybind11.h>
namespace py = pybind11;
PYBIND11_MODULE(foo, m) {
m.doc() = "hello, foo";
py::class_<Foo>(m, "Foo").def(py::init<>());
}
In another lib, this now works:
class MySystem : Foo {};
PYBIND11_MODULE(my_module, m) {
py::class_<MySystem, Foo>(m, "MySystem").def(py::init<>());
}
Does it fix it if you add py::module::import("pydrake.systems.framework"); to your PYBIND11_MODULE before trying to define your class?
For any C++ classes used by a pybind11 binding that are from other modules, you need to py::import that module before you can inherit from it (or use it as an argument, or etc).

Undefined reference to `ulocdata_open_63'

I am using ICU lib for Exemplar, I am getting undefined ref for `ulocdata_open_63'
I am not using "ulocdata_open_63" function but "ulocdata_open". Library is linked properly.
Why it is looking for ulocdata_open_63 definition even though I am not calling it.
Sample code:-
#include <stdio.h>
#define UNICODE
#include <unicode/uloc.h>
#include <unicode/ulocdata.h>
#include <unicode/urename.h>
typedef unsigned short U16;
int main()
{
char localeID[ULOC_FULLNAME_CAPACITY+ULOC_KEYWORD_AND_VALUES_CAPACITY] = "en_US";
UErrorCode icuStatus = U_ZERO_ERROR;
ULocaleData* uld = ulocdata_open("en", &icuStatus);
...
}
It looks you're linking against a ICU library that was built with ICU version suffixes, which is the default. To build a library without version suffixes you'll have to add the flag --disable-renaming to the configure build step of ICU4C.
See https://unicode-org.github.io/icu/userguide/icu4c/build.html#icu-as-a-system-level-library.

The rule of The Big Three

Iam confused with the below question I did the program as per my understanding but it crashes what am I doing wrong? If someone can please assist me it would be much appreciated.
my main.cpp looks like this:
#include <iostream>
#include <iomanip>
#include "Number.h"
using namespace std;
int main()
{
Number n1(10);
Number n2 = n1;
n2.printNum();
n2.addOne();
n1 = n2;
n1.printNum();
return 0;
}
Then my header file looks like this:
#include <iostream>
using namespace std;
class Number
{
int *p;
public:
Number(int);
void addOne();
void printNum();
};
And the below parts for the constructor I need to complete there where it shows comments that's the part I should complete:
#include <iostream>
#include "Number.h"
using namespace std;
Number::Number(int a1)
{
*p = a1;//write the code needed to initialise the value of the member variable with a1
}
void Number::printNum()
{
cout << "The number is " << *p << endl;
}
void Number::addOne()
{
*p++;//write the code needed to increment the value of the member variable by one.
}
Then the question asks the below what should I do to the code to use the BIG THREE?
Consider the following program. Complete the class definition (where you are asked to) and check the output. You can see that that program works without error once it is completed. However, experts suggest that in any class that uses pointers and the new operator it is better to follow the rule of The Big Three. Modify the class definition to follow the rule of The Big Three and submit the new program and the output. Demonstrate the use of this pointer.
Thank you
Rohan

Why VS2015 intellisense shows error on C++11 user defined literals (UDL)

The below code can be compiled and run, but VS2015 intellisense shows error. g++ & eclipse has the same issue (compiled & run but shows error)
Does anyone know how to fix it? I tried searching on google but hopeless.
The error is a little annoying.. :-)
#include <iostream>
#include <thread>
#include <chrono>
using namespace std;
using namespace std::literals;
using namespace chrono_literals;
int main()
{
this_thread::sleep_for(5s);
cout << "test \n";
return 0;
}
Error message: "Invalid suffix 's' on integer literal"
Thanks a lot!
You should add some #include statements and namespace references:
#include <iostream>
#include <chrono>
#include <thread>
int main()
{
using namespace std::literals::chrono_literals;
std::this_thread::sleep_for(5s);
std::cout << "test \n";
return 0;
}
In your code, the compiler is not been told to use namespace std. The 5s does not work without std::literals

create a boost::python::object from a noncopyable instance

I was wondering if any one here might be able to help me out with the following problem I'm having.
I seem unable to create a boost::python::object from a c++ class I've bound to python that is noncopyable. Here is a simplified example..
#include <boost/python.hpp>
class A
{
public:
static A*
create() {return new A;}
protected:
A(){}
};
void
doSomething(const A& a)
{
boost::python::object obj(a);
}
BOOST_PYTHON_MODULE(test)
{
boost::python::class_<A, boost::noncopyable>("A", boost::python::no_init)
.def("__init__", boost::python::make_constructor(&A::create));
boost::python::def("doSomething", &doSomething);
}
Then at runtime in python
import test
a = test.A()
test.doSomething(a)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: No to_python (by-value) converter found for C++ type: A
I realise that the boost::noncopyable parameter prevents a to_python converter for A being registered. Does anyone know how I might be able to create a boost::python::object from an A instance ?
thanks in advance!
Use this
boost::python::object obj(**boost::cref(a)**);