implementing reduce protocol in C
Tom Widrick
lordmacro at hotmail.com
Fri Sep 20 18:37:33 EDT 2002
"Alex Martelli"
> I recommend you use "ANSI C" style as a habit:
>
> static PyObject*
> proto_reduce(HyProtoObject* self)
That's what I get for copy/pasting from the python source code.
> Rather, you probably want to expose a factory function to be
> passed as the first item in the tuple returned by __reduce__
> (you may then want to return a 2-items tuple rather than a
> 3-items one from __reduce__, perhaps). Just make sure said
> first item exposes an attribute named __safe_for_unpickling__
> with a true value, or register it as a "safe constructor" with
> module copy_reg.
If it's not one thing, it's another. I decided to try this route but have
been barricaded again. I stuck a _build function in the module
method table and used copy_reg in the init function to make it a
"safe constructor."
module = PyImport_ImportModule("copy_reg");
if(module == NULL)
return;
method = PyDict_GetItemString(PyModule_GetDict(module), "constructor");
if(method == NULL)
return;
func = Py_FindMethod(mod_methodlist, NULL, "_build");
if(func == NULL)
return;
args = PyObject_CallFunction(method, "(O)", func);
Py_DECREF(func);
if(args == NULL)
return;
else
Py_DECREF(args);
Now cPickle is complaining that _build is not
found as __main__._build. I tried, in my python script, to directly
stick it in the namespace, but it says it's not the same.
from proto import proto
import cPickle
Root = proto('Root')
Root.spam = 'spam'
d = cPickle.dumps(Root)
cPickle.PicklingError: Can't pickle <built-in function _build>: it's not
found a
s __main__._build
and when I put
from proto import proto, _build
cPickle.PicklingError: Can't pickle <built-in function _build>: it's not the
sam
e object as __main__._build
I was easily able to do this in pure python using copy_reg, but the reason
why
I even started to port this type to C was because it was pickling/unpickling
too slowly.
I have a feeling this has something to do with wrapping the function object
from C into python.
My next attempt will be to create a factory type, like _protobuilder, that
will
be the first element of the tuple returned by __reduce__. I have the
pickling
working, now I just have to figure out how to make _protobuilder return a
proto object.
Tom
More information about the Python-list
mailing list