[pypy-commit] pypy reorder-map-attributes: refactor: actually introduce a really elidable function (as opposed to a fake
cfbolz
pypy.commits at gmail.com
Tue Feb 16 09:03:56 EST 2016
Author: Carl Friedrich Bolz <cfbolz at gmx.de>
Branch: reorder-map-attributes
Changeset: r82281:b2cf73983594
Date: 2016-02-16 10:01 +0000
http://bitbucket.org/pypy/pypy/changeset/b2cf73983594/
Log: refactor: actually introduce a really elidable function (as opposed
to a fake one)
diff --git a/pypy/objspace/std/mapdict.py b/pypy/objspace/std/mapdict.py
--- a/pypy/objspace/std/mapdict.py
+++ b/pypy/objspace/std/mapdict.py
@@ -188,14 +188,41 @@
obj._set_mapdict_map(self)
obj._mapdict_write_storage(self.storageindex, w_value)
+
+ @jit.elidable
+ def _find_branch_to_move_into(self, name, index):
+ # walk up the map chain to find an ancestor with lower order that
+ # already has the current name as a child inserted
+ current_order = sys.maxint
+ number_to_readd = 0
+ current = self
+ key = (name, index)
+ while True:
+ attr = None
+ if current.cache_attrs is not None:
+ attr = current.cache_attrs.get(key, None)
+ if attr is None or attr.order > current_order:
+ # we reached the top, so we didn't find it anywhere,
+ # just add it to the top attribute
+ if not isinstance(current, PlainAttribute):
+ return 0, self._get_new_attr(name, index)
+
+ else:
+ return number_to_readd, attr
+ # if not found try parent
+ number_to_readd += 1
+ current_order = current.order
+ current = current.back
+
@jit.look_inside_iff(lambda self, obj, name, index, w_value:
jit.isconstant(self) and
jit.isconstant(name) and
jit.isconstant(index))
def _reorder_and_add(self, obj, name, index, w_value):
- # the idea is as follows: the subtrees of any map are ordered by insertion.
- # the invariant is that subtrees that are inserted later must not contain
- # the name of the attribute of any earlier inserted attribute anywhere
+ # the idea is as follows: the subtrees of any map are ordered by
+ # insertion. the invariant is that subtrees that are inserted later
+ # must not contain the name of the attribute of any earlier inserted
+ # attribute anywhere
# m______
# inserted first / \ ... \ further attributes
# attrname a 0/ 1\ n\
@@ -217,41 +244,23 @@
while True:
current = self
number_to_readd = 0
- current_order = sys.maxint
- # walk up the map chain to find an ancestor with lower order that
- # already has the current name as a child inserted
- while True:
- attr = current._get_cache_attr(name, index)
- if attr is None or attr.order > current_order:
- # we reached the top, so we didn't find it anywhere,
- # just add it
- if not isinstance(current, PlainAttribute):
- self._add_attr_without_reordering(obj, name, index, w_value)
- break
-
- # if not found try parent
- else:
- number_to_readd += 1
- current_order = current.order
- current = current.back
- else:
- # we found the attributes further up, need to save the
- # previous values of the attributes we passed
- if number_to_readd:
- if stack_maps is None:
- stack_maps = [None] * self.length()
- stack_values = [None] * self.length()
- current = self
- for i in range(number_to_readd):
- assert isinstance(current, PlainAttribute)
- w_self_value = obj._mapdict_read_storage(
- current.storageindex)
- stack_maps[stack_index] = current
- stack_values[stack_index] = w_self_value
- stack_index += 1
- current = current.back
- attr._switch_map_and_write_storage(obj, w_value)
- break
+ number_to_readd, attr = self._find_branch_to_move_into(name, index)
+ # we found the attributes further up, need to save the
+ # previous values of the attributes we passed
+ if number_to_readd:
+ if stack_maps is None:
+ stack_maps = [None] * self.length()
+ stack_values = [None] * self.length()
+ current = self
+ for i in range(number_to_readd):
+ assert isinstance(current, PlainAttribute)
+ w_self_value = obj._mapdict_read_storage(
+ current.storageindex)
+ stack_maps[stack_index] = current
+ stack_values[stack_index] = w_self_value
+ stack_index += 1
+ current = current.back
+ attr._switch_map_and_write_storage(obj, w_value)
if not stack_index:
return
More information about the pypy-commit
mailing list