Python: using `copyreg` to define reducers for types that already have reducers

(Keep in mind that I work in Python 3, so the solution should work in Python 3.)

I would like to use a module copyregto teach Python how to saw functions. When I tried to do this, the object _Picklerwould still try to expand the functions using the function save_global. (What does not work for unrelated methods and what is the motivation for this.)

It seems to be _Picklertrying to look first in its own dispatchfor the type of object you want to sort before looking in copyreg.dispatch_table. I am not sure if this is intentional.

Is there any way for me to tell Python to uncover functions using the reducer that I provide?

+5
source share
1 answer

In Python 3.1, the following hack works:

import copyreg
def functionpickler(f):
  print('pickling', f.__name__)
  return f.__name__

ft = type(functionpickler)
copyreg.pickle(ft, functionpickler)

import pickle
pickle.Pickler = pickle._Pickler
del pickle.Pickler.dispatch[ft]

s = pickle.dumps(functionpickler)
print('Result is', s)

From this, two hacker lines:

pickle.Pickler = pickle._Pickler
del pickle.Pickler.dispatch[ft]

You need to delete the entry dispatchfor the function type, because otherwise it unloads the registration of copyreg; and I don’t think you can do it on a C-encoded Pickler, so you need to install it on a Python-encoded one.

It would be a little less hacking a subclass _Picklerwith its own class that does its own dispatch(copying the parent element and deleting the entry for the function type), and then use your subclass specifically (and its dump method), rather than pickle.dump; however, it would also be a little less convenient if this monkey were to pickle.

+1

All Articles