trydiff: use sets, not lists, for containment checks
authorMartin von Zweigbergk <martinvonz@google.com>
Tue, 23 Dec 2014 10:41:45 -0800
changeset 23661 dbd60f8d88d5
parent 23660 1ec6dbb9b216
child 23662 bc7d90c966d2
trydiff: use sets, not lists, for containment checks This only has a noticeable effect on diffs touching A LOT of files. For example, it takes hg diff -r FIREFOX_AURORA_30_BASE -r FIREFOX_AURORA_35_BASE from 1m55.465s to 1m32.354s. That diff has over 50k files.
mercurial/patch.py
--- a/mercurial/patch.py	Wed Dec 24 13:33:01 2014 -0600
+++ b/mercurial/patch.py	Tue Dec 23 10:41:45 2014 -0800
@@ -1794,6 +1794,7 @@
     if opts.git:
         revs = None
 
+    modifiedset, addedset, removedset = set(modified), set(added), set(removed)
     for f in sorted(modified + added + removed):
         to = None
         tn = None
@@ -1801,11 +1802,11 @@
         header = []
         if f in man1:
             to = getfilectx(f, ctx1).data()
-        if f not in removed:
+        if f not in removedset:
             tn = getfilectx(f, ctx2).data()
         a, b = f, f
         if opts.git or losedatafn:
-            if f in added or (f in modified and to is None):
+            if f in addedset or (f in modifiedset and to is None):
                 mode = gitmode[ctx2.flags(f)]
                 if f in copy or f in copyto:
                     if opts.git:
@@ -1815,7 +1816,7 @@
                             a = copyto[f]
                         omode = gitmode[man1.flags(a)]
                         addmodehdr(header, omode, mode)
-                        if a in removed and a not in gone:
+                        if a in removedset and a not in gone:
                             op = 'rename'
                             gone.add(a)
                         else:
@@ -1841,12 +1842,12 @@
                 if not opts.git and not tn:
                     # regular diffs cannot represent new empty file
                     losedatafn(f)
-            elif f in removed or (f in modified and tn is None):
+            elif f in removedset or (f in modifiedset and tn is None):
                 if opts.git:
                     # have we already reported a copy above?
-                    if ((f in copy and copy[f] in added
+                    if ((f in copy and copy[f] in addedset
                          and copyto[copy[f]] == f) or
-                        (f in copyto and copyto[f] in added
+                        (f in copyto and copyto[f] in addedset
                          and copy[copyto[f]] == f)):
                         dodiff = False
                     else: