Johan Råde
Johan Råde

Reputation: 21418

How should __nonzero__ be implemented using the Python C-API?

How should __nonzero__ be implemented using the Python C-API?

The reason I'm asking is that I'm trying to fix a bug in some Python C-API code. There a __nonzero__ method is added to the methods table as follows:

static PyMethodDef PyFoo_methods[] = {
    ...
    { (char*)"__nonzero__", (PyCFunction)_Foo_nonzero, METH_KEYWORDS|METH_VARARGS, NULL },
    ...
};

PyTypeObject PyFoo_Type = {
    PyObject_HEAD_INIT(NULL),
    0,  
    ....
    (struct PyMethodDef*)PyFoo_methods, /* tp_methods */
    ...
};

However, when I test the code, bool() applied to a Foo object always returns True; the _Foo_nonzero function is never called.

What is wrong with the code?

Upvotes: 2

Views: 497

Answers (1)

Thomas Wouters
Thomas Wouters

Reputation: 133495

Type customization in C is not done through specific methods in the method struct, but by filling particular fields of the PyTypeObject struct. In the case of __nonzero__, the C equivalent is the nb_nonzero member of the PyNumberMethods struct, which is pointed to by the tp_as_number member in the PyTypeObject struct: http://docs.python.org/c-api/typeobj.html#number-object-structures

Upvotes: 2

Related Questions