Mercurial > hg
changeset 39481:b6a0e06b0f7d
lazyancestors: extract __iter__ to free function
The next patch will keep a reference to the returned iterator in a
field, which would otherwise result in a reference cycle.
Differential Revision: https://phab.mercurial-scm.org/D4517
author | Martin von Zweigbergk <martinvonz@google.com> |
---|---|
date | Sun, 09 Sep 2018 23:16:55 -0700 |
parents | 89630d0b3e23 |
children | 77a2f6d805f2 |
files | mercurial/ancestor.py |
diffstat | 1 files changed, 34 insertions(+), 30 deletions(-) [+] |
line wrap: on
line diff
--- a/mercurial/ancestor.py Thu Aug 30 01:53:21 2018 +0200 +++ b/mercurial/ancestor.py Sun Sep 09 23:16:55 2018 -0700 @@ -259,6 +259,37 @@ missing.reverse() return missing +# Extracted from lazyancestors.__iter__ to avoid a reference cycle +def _lazyancestorsiter(parentrevs, initrevs, stoprev, inclusive): + seen = {nullrev} + revs = initrevs + + schedule = heapq.heappush + nextitem = heapq.heappop + see = seen.add + + if inclusive: + visit = [-r for r in revs] + seen.update(revs) + heapq.heapify(visit) + else: + visit = [] + heapq.heapify(visit) + for r in revs: + for parent in parentrevs(r): + if parent not in seen: + schedule(visit, -parent) + see(parent) + + while visit: + current = -nextitem(visit) + if current >= stoprev: + yield current + for parent in parentrevs(current): + if parent not in seen: + schedule(visit, -parent) + see(parent) + class lazyancestors(object): def __init__(self, pfunc, revs, stoprev=0, inclusive=False): """Create a new object generating ancestors for the given revs. Does @@ -311,36 +342,9 @@ If inclusive is True, the source revisions are also yielded. The reverse revision number order is still enforced.""" - seen = {nullrev} - revs = self._initrevs - - parentrevs = self._parentrevs - stoprev = self._stoprev - schedule = heapq.heappush - nextitem = heapq.heappop - see = seen.add - - if self._inclusive: - visit = [-r for r in revs] - seen.update(revs) - heapq.heapify(visit) - else: - visit = [] - heapq.heapify(visit) - for r in revs: - for parent in parentrevs(r): - if parent not in seen: - schedule(visit, -parent) - see(parent) - - while visit: - current = -nextitem(visit) - if current >= stoprev: - yield current - for parent in parentrevs(current): - if parent not in seen: - schedule(visit, -parent) - see(parent) + for rev in _lazyancestorsiter(self._parentrevs, self._initrevs, + self._stoprev, self._inclusive): + yield rev def __contains__(self, target): """Test whether target is an ancestor of self._initrevs."""