ObjectStoreGraphWalker.ack: use non-recursive implementation
authorTay Ray Chuan <rctay89@gmail.com>
Fri, 9 Apr 2010 23:36:28 +0000 (01:36 +0200)
committerJelmer Vernooij <jelmer@samba.org>
Fri, 9 Apr 2010 23:36:28 +0000 (01:36 +0200)
We were recursively removing from self.heads; rewrite this such we try
removing heads this in a loop.

This gives a nice performance boost.

dulwich/object_store.py

index cad7bd671b1df254cb22ce05cfcbd935b687a298..d3e70317c325bdea036898c6c8eec140a664200a 100644 (file)
@@ -706,11 +706,25 @@ class ObjectStoreGraphWalker(object):
 
     def ack(self, sha):
         """Ack that a revision and its ancestors are present in the source."""
-        if sha in self.heads:
-            self.heads.remove(sha)
-        if sha in self.parents:
-            for p in self.parents[sha]:
-                self.ack(p)
+        ancestors = set([sha])
+
+        # stop if we run out of heads to remove
+        while self.heads:
+            for a in ancestors:
+                if a in self.heads:
+                    self.heads.remove(a)
+
+            # collect all ancestors
+            new_ancestors = set()
+            for a in ancestors:
+                if a in self.parents:
+                    new_ancestors.update(self.parents[a])
+
+            # no more ancestors; stop
+            if not new_ancestors:
+                break
+
+            ancestors = new_ancestors
 
     def next(self):
         """Iterate over ancestors of heads in the target."""