In order to be able to pickle a nested function (for multiprocessing), I decorated the nested function with the decorator:
def globalize_one(func):
def wrapper_one(*args,**kwargs):
return func(*args,**kwargs)
setattr(modules['__main__'],'sdfsdf',wrapper_one)
return wrapper_one
However, this decorator does not work, when I ran this
def test_one():
@globalize_one
def inside_one():
return 1
try:
pickle.dumps(inside_one)
except Exception as e:
print(e)
test_one()
I received the exception Can't pickle local object 'globalize_one.<locals>.wrapper_one'
To make the decorator work, all I need is to change the __qualname__
of wrapper_one
to sdfsdf
in globalize_one
right before the line setattr(modules['__main__'],'sdfsdf',wrapper_one)
.
def globalize_two(func):
def wrapper_two(*args,**kwargs):
return func(*args,**kwargs)
# the single extra line as compared to globalize_one
wrapper_two.__qualname__ = 'sdfsdf'
setattr(modules['__main__'],'sdfsdf',wrapper_two)
return wrapper_two
def test_two():
@globalize_two
def inside_two():
return 1
try:
pickle.dumps(inside_two)
except Exception as e:
print(e)
As you can see by running the code, the nested function inside_two
can be pickled now.
My confusion is, why by changing the __qualname__
, the decorator will work properly? I thought changing the name of a function have no real effect.