Patchwork [1,of,3,V3,part,1] revlog.ancestors: add support for including revs

login
register
mail settings
Submitter Siddharth Agarwal
Date Dec. 17, 2012, 11:19 p.m.
Message ID <cc32dcb345b6e9d0f2b8.1355786375@sid0x220>
Download mbox | patch
Permalink /patch/174/
State Accepted
Commit f88c60e740a15fe43ac8fa8b9b702c7966205e86
Headers show

Comments

Siddharth Agarwal - Dec. 17, 2012, 11:19 p.m.
# HG changeset patch
# User Siddharth Agarwal <sid0 at fb.com>
# Date 1355786031 28800
# Node ID cc32dcb345b6e9d0f2b85bdd63e8262d7e12ac2a
# Parent  4fc691813acda0328613202e0952af5c3d2109ad
revlog.ancestors: add support for including revs

This is in preparation for an upcoming refactoring. This also fixes a bug in
incancestors, where if an element of revs was an ancestor of another it would
be generated twice.

Patch

diff -r 4fc691813acd -r cc32dcb345b6 mercurial/revlog.py
--- a/mercurial/revlog.py	Tue Nov 13 16:16:14 2012 -0800
+++ b/mercurial/revlog.py	Mon Dec 17 15:13:51 2012 -0800
@@ -341,17 +341,27 @@ 
         return len(t)
     size = rawsize
 
-    def ancestors(self, revs, stoprev=0):
+    def ancestors(self, revs, stoprev=0, inclusive=False):
         """Generate the ancestors of 'revs' in reverse topological order.
         Does not generate revs lower than stoprev.
 
-        Yield a sequence of revision numbers starting with the parents
-        of each revision in revs, i.e., each revision is *not* considered
-        an ancestor of itself.  Results are in breadth-first order:
-        parents of each rev in revs, then parents of those, etc.  Result
-        does not include the null revision."""
+        If inclusive is False, yield a sequence of revision numbers starting
+        with the parents of each revision in revs, i.e., each revision is *not*
+        considered an ancestor of itself.  Results are in breadth-first order:
+        parents of each rev in revs, then parents of those, etc.
+
+        If inclusive is True, yield all the revs first (ignoring stoprev),
+        then yield all the ancestors of revs as when inclusive is False.
+        If an element in revs is an ancestor of a different rev it is not
+        yielded again.
+
+        Result does not include the null revision."""
         visit = util.deque(revs)
         seen = set([nullrev])
+        if inclusive:
+            for rev in revs:
+                yield rev
+            seen.update(revs)
         while visit:
             for parent in self.parentrevs(visit.popleft()):
                 if parent < stoprev:
@@ -364,10 +374,7 @@ 
     def incancestors(self, revs, stoprev=0):
         """Identical to ancestors() except it also generates the
         revisions, 'revs'"""
-        for rev in revs:
-            yield rev
-        for rev in self.ancestors(revs, stoprev):
-            yield rev
+        return self.ancestors(revs, stoprev, inclusive=True)
 
     def descendants(self, revs):
         """Generate the descendants of 'revs' in revision order.
diff -r 4fc691813acd -r cc32dcb345b6 tests/test-revlog-ancestry.py
--- a/tests/test-revlog-ancestry.py	Tue Nov 13 16:16:14 2012 -0800
+++ b/tests/test-revlog-ancestry.py	Mon Dec 17 15:13:51 2012 -0800
@@ -62,6 +62,14 @@ 
     for r in repo.changelog.ancestors([7], 6):
         print r,
 
+    print '\nAncestors of 7, including revs'
+    for r in repo.changelog.ancestors([7], inclusive=True):
+        print r,
+
+    print '\nAncestors of 7, 5 and 3, including revs'
+    for r in repo.changelog.ancestors([7, 5, 3], inclusive=True):
+        print r,
+
     # Descendants
     print '\n\nDescendants of 5'
     for r in repo.changelog.descendants([5]):
diff -r 4fc691813acd -r cc32dcb345b6 tests/test-revlog-ancestry.py.out
--- a/tests/test-revlog-ancestry.py.out	Tue Nov 13 16:16:14 2012 -0800
+++ b/tests/test-revlog-ancestry.py.out	Mon Dec 17 15:13:51 2012 -0800
@@ -6,6 +6,10 @@ 
 4 2 0 
 Ancestors of 7, stop at 6
 6 
+Ancestors of 7, including revs
+7 6 5 3 4 2 1 0 
+Ancestors of 7, 5 and 3, including revs
+7 5 3 6 4 2 1 0 
 
 Descendants of 5
 7 8