boost:python::arg and default value
Hi. I want to resolve the issue discussed in this thread: http://thread.gmane.org/gmane.comp.python.c++/9878/focus=9881 The short version of the discussion is: class Foo; class Foo2 { friend class Foo; Foo2(Foo *f=0); }; class Foo { Foo(Foo2 *f=0); }; It is not possible to expose both Foo and Foo2 constructors with default values, without usage of some tricks. The main problem is that, when Boost.Python initializes boost::python::arg, it requires type of default value to be registered. I had some free time and took a look on the code. I think, I understand what is going on and how to fix the situation, but still need some help here and there. I see only one possible solution - to add to Boost.Python functionality, that will allow user to control argument default value conversion time. Today, the default value converted to Python during function registration. This happens in boost::python::objects::function class constructor. Solution: 1. To add classes that will define C++ to Python convert time. struct converter_base{ virtual handle<> py_value() const = 0; //const in interface is a hack, objects::function::call member function //has const modifier }; struct default_converter : converter_base{ converts value in the constructor and saves the value in a member variable py_value returns the member variable }; struct on_first_use_converter : converter_base{ saves the C++ value as member variable py_value will convert C++ value to Python on first invocation, will save the result in member variable, after this, it will always return the member variable. }; 2. Change in keyword struct. Today keyword struct keeps function default value as instance of handle<>. This should be changed. keyword struct should keep shared_ptr to coverter_base class instance or it should keep empty shared_ptr. Thus it will be possible to control C++ to Python default value conversion time from objects::function class. 3. There are few changes, that should be done to boost::python::objects::function class. This is the place I have lack of knowledge and the code is a little bit complex and fragile. More over, every additional logic, that will be added here will downgrade performance. There are few changed that should be done to the class. 1. The class should keep all keywords, that has default value converter other than default_converter. It also should save keyword position. 2. In constructor, when we register function keyword arguments, we should skip initialization of default value, for converters other than default_converter. 3. Now, the only change left is to modify function::call method. Unfortunately I can not write the working code - lack of knowledge( or sleep ). I'll be glad, if somebody can help me here. The main problem, is that some how I should pass to the function default values and I don't exactly understand how I should do that. I attached the modified files. What do you think about those changes? -- Roman Yakovenko C++ Python language binding http://www.language-binding.net/
"Roman Yakovenko" <roman.yakovenko@gmail.com> writes:
Hi. I want to resolve the issue discussed in this thread: http://thread.gmane.org/gmane.comp.python.c++/9878/focus=9881
The short version of the discussion is:
class Foo;
class Foo2 { friend class Foo; Foo2(Foo *f=0); };
class Foo { Foo(Foo2 *f=0); };
It is not possible to expose both Foo and Foo2 constructors with default values, without usage of some tricks. The main problem is that, when Boost.Python initializes boost::python::arg, it requires type of default value to be registered.
I had some free time and took a look on the code. I think, I understand what is going on and how to fix the situation, but still need some help here and there.
I see only one possible solution - to add to Boost.Python functionality, that will allow user to control argument default value conversion time.
I disagree. It should be lazy and do the conversion on demand. Extra control is not a significant benefit in this instance. -- Dave Abrahams Boost Consulting www.boost-consulting.com
On 8/31/06, David Abrahams <dave@boost-consulting.com> wrote:
I see only one possible solution - to add to Boost.Python functionality, that will allow user to control argument default value conversion time.
I disagree. It should be lazy and do the conversion on demand. Extra control is not a significant benefit in this instance.
Does "lazy and on demand" mean first time a user calls function? If so, I will try to work on the patch, but I think I still will need help with boost::python::objects::function class. -- Roman Yakovenko C++ Python language binding http://www.language-binding.net/
"Roman Yakovenko" <roman.yakovenko@gmail.com> writes:
On 8/31/06, David Abrahams <dave@boost-consulting.com> wrote:
I see only one possible solution - to add to Boost.Python functionality, that will allow user to control argument default value conversion time.
I disagree. It should be lazy and do the conversion on demand. Extra control is not a significant benefit in this instance.
Does "lazy and on demand" mean first time a user calls function?
Yes... or even the first time a user actually uses the default.
If so, I will try to work on the patch, but I think I still will need help with boost::python::objects::function class.
I'll do my best to help -- Dave Abrahams Boost Consulting www.boost-consulting.com
participants (2)
-
David Abrahams -
Roman Yakovenko