Open N-Coder opened 1 year ago
This also affects bind_object
, although that function doesn't use AddTypeName and only checks for __name__
, so my fix wouldn't work there:
>>> cppyy.bind_object(cppyy.nullptr, g.Test)
<cppyy.gbl.Test object at 0x(nil)>
>>> cppyy.bind_object(cppyy.nullptr, g.testptr)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: bind_object expects a valid class or class name as an argument
Background on this is that I have a method similar to the testfun
below, which is pretty hard to call when you want to pass a nullptr:
>>> cppyy.cppdef("template<typename T> void testfun(T const& x) {}")
True
>>> g.testfun["testptr"](cppyy.nullptr)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: Could not find "testfun<testptr>" (set cppyy.set_debug() for C++ errors):
none of the 2 overloaded methods succeeded. Full details:
void ::testfun(Test*const& x) =>
TypeError: could not convert argument 1
void ::testfun(Test*const& x) =>
TypeError: could not convert argument 1
none of the 3 overloaded methods succeeded. Full details:
void ::testfun(Test*const& x) =>
TypeError: could not convert argument 1
void ::testfun(Test*const& x) =>
TypeError: could not convert argument 1
void ::testfun(Test*const& x) =>
TypeError: could not convert argument 1
>>> g.testfun["testptr"](cppyy.bind_object(cppyy.nullptr, g.Test)) # succeeds
It would be super awesome if I could just write g.testfun[g.testptr](cppyy.nullptr)
or even g.testfun[g.testptr](None)
.
That last error is separate from the problem of the using: nullptr
pointer is simply not accepted for T* const&
, whereas the typed pointer is. But yes, TypedefPointerToClass
should have a __cpp_name__
(and a __name__
for that matter :) ).
The original issue is fixed in repo.
The original issue is fixed in repo.
Awesome, thanks a lot!
nullptr
pointer is simply not accepted forT* const&
Could you elaborate a little on this? I don't quite understand why casting the nullptr with cppyy.bind_object(cppyy.nullptr, g.Test)
should behave differently from cppyy.nullptr
here...
cppyy.nullptr
is a unique Python object, so that it can be pointer compared, which is nice and fast. It's not a CPPInstance
type, which you get by binding nullptr
. The code that handles T*const&
does not have a check for nullptr
to let it pass. Might have been a quick fix, except that there wasn't already a distinction between T*const&
and T*&
, which for nullptr
there should be.
Using a type name defined via
using
as template argument currently fails, while using class objects works fine:Furthermore, inspecting the
TypedefPointerToClass
in Python is pretty hard, as its only exposed method is the constructor.A simple fix might be defining
__cpp_name__
as the name used in theusing
declaration for the TypedefPointerToClass, i.e. havingg.testptr.__cpp_name__ == "testptr"
, as that would be recognized correctly by the AddTypeName function used for constructing the template arguments. A second method for getting the name the declaration points to (and translating that string into a type object) would of course also be nice.