"Jim Bosch" wrote in message news:4e4ad9d9.9000...@gmail.com...
Unfortunately, there's no "best-match" type checking in Boost.Python; when
trying to convert a Python object to a particular C++ type, it simply runs
over a list of all the converters registered (using RTTI) for that C++
type.
Each of those converters then gets a chance to check whether it "matches"
the Python object; if it thinks it does, none of the other converters get
tried.
I'd guess that's what's happening to you - implicitly_convertible doesn't
really do enough work in that match stage, so the first conversion you've
registered says "I match!" and then fails by throwing an exception.
The fix might be in how you've written your vector<> conversions; when
given a list or tuple that contains the wrong element type, they need to
report that they "don't match", rather than matching any list or tuple and
then throwing an exception when the element type is incorrect.
Good luck!
Jim Bosch
I change my vector<> conversion(see it in my last reply) to add
specialization for int, float, string etc.
I added type check in convertible() function:
template <>
struct vector_from_python <float>
{
vector_from_python()
{
python::converter::registry::push_back(&convertible, &construct,
python::type_id<vector<float>
>());
}
static void* convertible(PyObject* obj_ptr)
{
if (!(PyList_Check(obj_ptr) || PyTuple_Check(obj_ptr)
|| PyIter_Check(obj_ptr) || PyRange_Check(obj_ptr))) {
return 0;
}
PyObject * first_obj = PyObject_GetItem(obj_ptr,
PyInt_FromLong(0));
if( !PyObject_TypeCheck(first_obj, &PyFloat_Type) ) {
return 0;
}
return obj_ptr;
}
static void construct(PyObject* obj_ptr,
python::converter::rvalue_from_python_stage1_data*
data)
{
void* storage =
((python::converter::rvalue_from_python_storage<vector<float> >*)
data)->storage.bytes;
new (storage) vector<float>();
data->convertible = storage;
vector<float>& result = *((vector<float>*) storage);
python::handle<> obj_iter(PyObject_GetIter(obj_ptr));
while(1) {
python::handle<>
py_elem_hdl(python::allow_null(PyIter_Next(obj_iter.get())));
if (PyErr_Occurred()) {
python::throw_error_already_set();
}
if (!py_elem_hdl.get()) {
break;
}
python::object py_elem_obj(py_elem_hdl);
python::extract<float> elem_proxy(py_elem_obj);
result.push_back(elem_proxy());
}
}
};
This time the implicit type conversion works perfectly. But I got a new
problem: the memory leak!
The memory leak happens only for float type, whenever I convert the float
list in python to vector
of float in c++, the memory for float list is leaked. I put the call in a
function, and called the gc.collect()
after exit the function, the memory is still not recycled.
Why is the memory of the python list is not freed after exit the scope?
Grant
_______________________________________________
Cplusplus-sig mailing list
Cplusplus-sig@python.org
http://mail.python.org/mailman/listinfo/cplusplus-sig