This commit is contained in:
Brett Cannon 2013-06-14 18:33:21 -04:00
commit 8c18da20f9
5 changed files with 32 additions and 3 deletions

View file

@ -27,6 +27,10 @@ The :mod:`filecmp` module defines the following functions:
Note that no external programs are called from this function, giving it Note that no external programs are called from this function, giving it
portability and efficiency. portability and efficiency.
This function uses a cache for past comparisons and the results,
with a cache invalidation mechanism relying on stale signatures
or by explicitly calling :func:`clear_cache`.
.. function:: cmpfiles(dir1, dir2, common, shallow=True) .. function:: cmpfiles(dir1, dir2, common, shallow=True)
@ -48,6 +52,15 @@ The :mod:`filecmp` module defines the following functions:
one of the three returned lists. one of the three returned lists.
.. function:: clear_cache()
.. versionadded:: 3.4
Clear the filecmp cache. This may be useful if a file is compared so quickly
after it is modified that it is within the mtime resolution of
the underlying filesystem.
.. _dircmp-objects: .. _dircmp-objects:
The :class:`dircmp` class The :class:`dircmp` class

View file

@ -6,6 +6,7 @@ Classes:
Functions: Functions:
cmp(f1, f2, shallow=True) -> int cmp(f1, f2, shallow=True) -> int
cmpfiles(a, b, common) -> ([], [], []) cmpfiles(a, b, common) -> ([], [], [])
clear_cache()
""" """
@ -13,7 +14,7 @@ import os
import stat import stat
from itertools import filterfalse from itertools import filterfalse
__all__ = ['cmp', 'dircmp', 'cmpfiles', 'DEFAULT_IGNORES'] __all__ = ['clear_cache', 'cmp', 'dircmp', 'cmpfiles', 'DEFAULT_IGNORES']
_cache = {} _cache = {}
BUFSIZE = 8*1024 BUFSIZE = 8*1024
@ -21,6 +22,9 @@ BUFSIZE = 8*1024
DEFAULT_IGNORES = [ DEFAULT_IGNORES = [
'RCS', 'CVS', 'tags', '.git', '.hg', '.bzr', '_darcs', '__pycache__'] 'RCS', 'CVS', 'tags', '.git', '.hg', '.bzr', '_darcs', '__pycache__']
def clear_cache():
"""Clear the filecmp cache."""
_cache.clear()
def cmp(f1, f2, shallow=True): def cmp(f1, f2, shallow=True):
"""Compare two files. """Compare two files.
@ -39,7 +43,8 @@ def cmp(f1, f2, shallow=True):
True if the files are the same, False otherwise. True if the files are the same, False otherwise.
This function uses a cache for past comparisons and the results, This function uses a cache for past comparisons and the results,
with a cache invalidation mechanism relying on stale signatures. with a cache invalidation mechanism relying on stale signatures
or by explicitly calling clear_cache().
""" """
@ -56,7 +61,7 @@ def cmp(f1, f2, shallow=True):
if outcome is None: if outcome is None:
outcome = _do_cmp(f1, f2) outcome = _do_cmp(f1, f2)
if len(_cache) > 100: # limit the maximum size of the cache if len(_cache) > 100: # limit the maximum size of the cache
_cache.clear() clear_cache()
_cache[f1, f2, s1, s2] = outcome _cache[f1, f2, s1, s2] = outcome
return outcome return outcome

View file

@ -39,6 +39,13 @@ class FileCompareTestCase(unittest.TestCase):
self.assertFalse(filecmp.cmp(self.name, self.dir), self.assertFalse(filecmp.cmp(self.name, self.dir),
"File and directory compare as equal") "File and directory compare as equal")
def test_cache_clear(self):
first_compare = filecmp.cmp(self.name, self.name_same, shallow=False)
second_compare = filecmp.cmp(self.name, self.name_diff, shallow=False)
filecmp.clear_cache()
self.assertTrue(len(filecmp._cache) == 0,
"Cache not cleared after calling clear_cache")
class DirCompareTestCase(unittest.TestCase): class DirCompareTestCase(unittest.TestCase):
def setUp(self): def setUp(self):
tmpdir = tempfile.gettempdir() tmpdir = tempfile.gettempdir()

View file

@ -738,6 +738,7 @@ Benno Leslie
Christopher Tur Lesniewski-Laas Christopher Tur Lesniewski-Laas
Alain Leufroy Alain Leufroy
Mark Levinson Mark Levinson
Mark Levitt
William Lewis William Lewis
Akira Li Akira Li
Xuanji Li Xuanji Li

View file

@ -123,6 +123,9 @@ Core and Builtins
Library Library
------- -------
- Issue #18149: Add filecmp.clear_cache() to manually clear the filecmp cache.
Patch by Mark Levitt
- Issue #18193: Add importlib.reload(). - Issue #18193: Add importlib.reload().
- Issue #18157: Stop using imp.load_module() in pydoc. - Issue #18157: Stop using imp.load_module() in pydoc.