[pypy-commit] pypy remove-dict-smm: Make descr_dictiter__length_hint__ and descr_dictiter__reduce__ methods.
Manuel Jacob
noreply at buildbot.pypy.org
Tue May 14 21:24:27 CEST 2013
Author: Manuel Jacob
Branch: remove-dict-smm
Changeset: r64095:e9e683af479a
Date: 2013-05-14 20:26 +0200
http://bitbucket.org/pypy/pypy/changeset/e9e683af479a/
Log: Make descr_dictiter__length_hint__ and descr_dictiter__reduce__
methods.
diff --git a/pypy/objspace/std/dictmultiobject.py b/pypy/objspace/std/dictmultiobject.py
--- a/pypy/objspace/std/dictmultiobject.py
+++ b/pypy/objspace/std/dictmultiobject.py
@@ -1014,6 +1014,61 @@
w_self.space = space
w_self.iteratorimplementation = iteratorimplementation
+ def descr_length_hint(self, space):
+ return space.wrap(self.iteratorimplementation.length())
+
+ def descr_reduce(self, space):
+ """
+ This is a slightly special case of pickling.
+ Since iteration over a dict is a bit hairy,
+ we do the following:
+ - create a clone of the dict iterator
+ - run it to the original position
+ - collect all remaining elements into a list
+ At unpickling time, we just use that list
+ and create an iterator on it.
+ This is of course not the standard way.
+
+ XXX to do: remove this __reduce__ method and do
+ a registration with copy_reg, instead.
+ """
+ w_mod = space.getbuiltinmodule('_pickle_support')
+ mod = space.interp_w(MixedModule, w_mod)
+ new_inst = mod.get('dictiter_surrogate_new')
+ w_typeobj = space.gettypeobject(dictiter_typedef)
+
+ raise OperationError(
+ space.w_TypeError,
+ space.wrap("can't pickle dictionary-keyiterator objects"))
+ # XXXXXX get that working again
+
+ # we cannot call __init__ since we don't have the original dict
+ if isinstance(self, W_DictIter_Keys):
+ w_clone = space.allocate_instance(W_DictIter_Keys, w_typeobj)
+ elif isinstance(self, W_DictIter_Values):
+ w_clone = space.allocate_instance(W_DictIter_Values, w_typeobj)
+ elif isinstance(self, W_DictIter_Items):
+ w_clone = space.allocate_instance(W_DictIter_Items, w_typeobj)
+ else:
+ msg = "unsupported dictiter type '%s' during pickling" % (self,)
+ raise OperationError(space.w_TypeError, space.wrap(msg))
+ w_clone.space = space
+ w_clone.content = self.content
+ w_clone.len = self.len
+ w_clone.pos = 0
+ w_clone.setup_iterator()
+ # spool until we have the same pos
+ while w_clone.pos < self.pos:
+ w_obj = w_clone.next_entry()
+ w_clone.pos += 1
+ stuff = [w_clone.next_entry() for i in range(w_clone.pos, w_clone.len)]
+ w_res = space.newlist(stuff)
+ tup = [
+ w_res
+ ]
+ w_ret = space.newtuple([new_inst, space.newtuple(tup)])
+ return w_ret
+
class W_DictMultiIterKeysObject(W_BaseDictMultiIterObject):
pass
@@ -1262,69 +1317,10 @@
# ____________________________________________________________
-def descr_dictiter__length_hint__(space, w_self):
- assert isinstance(w_self, W_BaseDictMultiIterObject)
- return space.wrap(w_self.iteratorimplementation.length())
-
-
-def descr_dictiter__reduce__(w_self, space):
- """
- This is a slightly special case of pickling.
- Since iteration over a dict is a bit hairy,
- we do the following:
- - create a clone of the dict iterator
- - run it to the original position
- - collect all remaining elements into a list
- At unpickling time, we just use that list
- and create an iterator on it.
- This is of course not the standard way.
-
- XXX to do: remove this __reduce__ method and do
- a registration with copy_reg, instead.
- """
- w_mod = space.getbuiltinmodule('_pickle_support')
- mod = space.interp_w(MixedModule, w_mod)
- new_inst = mod.get('dictiter_surrogate_new')
- w_typeobj = space.gettypeobject(dictiter_typedef)
-
- raise OperationError(
- space.w_TypeError,
- space.wrap("can't pickle dictionary-keyiterator objects"))
- # XXXXXX get that working again
-
- # we cannot call __init__ since we don't have the original dict
- if isinstance(w_self, W_DictIter_Keys):
- w_clone = space.allocate_instance(W_DictIter_Keys, w_typeobj)
- elif isinstance(w_self, W_DictIter_Values):
- w_clone = space.allocate_instance(W_DictIter_Values, w_typeobj)
- elif isinstance(w_self, W_DictIter_Items):
- w_clone = space.allocate_instance(W_DictIter_Items, w_typeobj)
- else:
- msg = "unsupported dictiter type '%s' during pickling" % (w_self, )
- raise OperationError(space.w_TypeError, space.wrap(msg))
- w_clone.space = space
- w_clone.content = w_self.content
- w_clone.len = w_self.len
- w_clone.pos = 0
- w_clone.setup_iterator()
- # spool until we have the same pos
- while w_clone.pos < w_self.pos:
- w_obj = w_clone.next_entry()
- w_clone.pos += 1
- stuff = [w_clone.next_entry() for i in range(w_clone.pos, w_clone.len)]
- w_res = space.newlist(stuff)
- tup = [
- w_res
- ]
- w_ret = space.newtuple([new_inst, space.newtuple(tup)])
- return w_ret
-
-# ____________________________________________________________
-
W_BaseDictMultiIterObject.typedef = StdTypeDef("dictionaryiterator",
- __length_hint__ = gateway.interp2app(descr_dictiter__length_hint__),
- __reduce__ = gateway.interp2app(descr_dictiter__reduce__),
+ __length_hint__ = gateway.interp2app(W_BaseDictMultiIterObject.descr_length_hint),
+ __reduce__ = gateway.interp2app(W_BaseDictMultiIterObject.descr_reduce),
)
# ____________________________________________________________
More information about the pypy-commit
mailing list