|
Boost : |
From: David Abrahams (david.abrahams_at_[hidden])
Date: 2001-11-14 08:33:48
----- Original Message -----
From: "Ivan A. Vigasin" <vig_at_[hidden]>
> Traceback (most recent call last):
> File "<stdin>", line 1, in ?
> File "<stdin>", line 5, in __init__
> TypeError: unbound method __init__() must be called with instance as
first argument
>
> ;((
>
> Maybe result depends on python's or boost's version?
Perhaps. What versions are you using?
The Boost code in question hasn't changed in a year. I was using
Python2.2b1, but it's hard to imagine that Python can get any control over
this! The code in question is at the bottom of the message.
Aha!
OK, I believe that Python2.2 is just being liberal, here. If you look at the
code below, Boost.Python only does that method unwinding when looking at
/base/ class attributes. So, this should work for you:
class Base:
def __init__(self):
self.x = 'x'
class BasePrime(Base):
__init_Base_ = Base.__init__
class Derived(A1,BasePrime):
def __init__(self):
A1.__init__(self)
self.__init_Base_()
self.y = 'y'
I guess it would be good to have a more explicit mechansim for this, eh?
Oh, please try this one as well:
class BasePrime(Base): pass
class Derived(A1,BasePrime):
def __init__(self):
A1.__init__(self)
BasePrime.__init__(self)
I think that one should work, too, and it's a bit more elegant.
-Dave
---------
ref local_attribute = m_name_space.get_item(string(name).reference());
if (local_attribute.get())
return local_attribute.release();
// In case there are no bases...
PyErr_SetString(PyExc_AttributeError, name);
// Check bases
for (std::size_t i = 0; i < m_bases.size(); ++i)
{
if (PyErr_ExceptionMatches(PyExc_AttributeError))
PyErr_Clear(); // we're going to try a base class
else if (PyErr_Occurred())
break; // Other errors count, though!
PyObject* base_attribute =
PyObject_GetAttrString(m_bases[i].get(), const_cast<char*>(name));
if (base_attribute != 0)
{
// Unwind the actual underlying function from unbound Python
class
// methods in case of multiple inheritance from real Python
// classes. Python stubbornly insists that the first argument
to a
// method must be a true Python instance object otherwise. Do
not
// unwrap bound methods; that would interfere with intended
semantics.
if (PyMethod_Check(base_attribute)
&&
reinterpret_cast<PyMethodObject*>(base_attribute)->im_self == 0)
{
PyObject* function
=
reinterpret_cast<PyMethodObject*>(base_attribute)->im_func;
Py_INCREF(function);
Py_DECREF(base_attribute);
return function;
}
else
{
return base_attribute;
}
}
}
Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk