diff options
| author | Julian Andres Klode <jak@debian.org> | 2009-04-15 14:16:28 +0200 |
|---|---|---|
| committer | Julian Andres Klode <jak@debian.org> | 2009-04-15 14:16:28 +0200 |
| commit | 2b867aebe32d59b7450f3a7fb22390e0dd9f8cc7 (patch) | |
| tree | 49d4d5ec7e109dfe55d51ffd2061c96ec18bd5da | |
| parent | 3caa05aa8e295d338be4bfbe7fdd2e825a59d947 (diff) | |
| download | python-apt-2b867aebe32d59b7450f3a7fb22390e0dd9f8cc7.tar.gz | |
* apt/cache.py: Use set() and WeakValueDictionary() for holding packages.
Only create Package objects when they are requested, do not keep them in
a dict. Saves 10MB for 25,000 packages on my machine.
The set holds the names of all packages which have at least one version,
and the WeakValueDictionary() holds weak references to created Package
objects.
This way accessing the same package two times should return the same object,
kept by the WeakValueDictionary().
| -rw-r--r-- | apt/cache.py | 38 | ||||
| -rw-r--r-- | debian/changelog | 4 |
2 files changed, 26 insertions, 16 deletions
diff --git a/apt/cache.py b/apt/cache.py index cc425ccb..d13010af 100644 --- a/apt/cache.py +++ b/apt/cache.py @@ -20,6 +20,7 @@ # USA import os +import weakref import apt_pkg from apt import Package @@ -80,7 +81,8 @@ class Cache(object): self._records = apt_pkg.GetPkgRecords(self._cache) self._list = apt_pkg.GetPkgSourceList() self._list.ReadMainList() - self._dict = {} + self._set = set() + self._weakref = weakref.WeakValueDictionary() progress.Op = "Building data structures" i=last=0 @@ -91,7 +93,7 @@ class Cache(object): last=i # drop stuff with no versions (cruft) if len(pkg.VersionList) > 0: - self._dict[pkg.Name] = Package(self, pkg) + self._set.add(pkg.Name) i += 1 @@ -100,30 +102,36 @@ class Cache(object): def __getitem__(self, key): """ look like a dictionary (get key) """ - return self._dict[key] + try: + return self._weakref[key] + except KeyError: + if key in self._set: + pkg = self._weakref[key] = Package(self, self._cache[key]) + return pkg + else: + raise KeyError('The cache has no package named %r' % key) def __iter__(self): - for pkgname in self._dict.keys(): - yield self._dict[pkgname] + for pkgname in self._set: + yield self[pkgname] raise StopIteration def has_key(self, key): - return (key in self._dict) + return (key in self._set) def __contains__(self, key): - return (key in self._dict) + return (key in self._set) def __len__(self): - return len(self._dict) + return len(self._set) def keys(self): - return self._dict.keys() + return list(self._set) def getChanges(self): """ Get the marked changes """ changes = [] - for name in self._dict.keys(): - p = self._dict[name] + for p in self: if p.markedUpgrade or p.markedInstall or p.markedDelete or \ p.markedDowngrade or p.markedReinstall: changes.append(p) @@ -348,7 +356,7 @@ class FilteredCache(object): return len(self._filtered) def __getitem__(self, key): - return self.cache._dict[key] + return self.cache[key] def __iter__(self): for pkgname in self._filtered: @@ -366,10 +374,10 @@ class FilteredCache(object): def _reapplyFilter(self): " internal helper to refilter " self._filtered = {} - for pkg in self.cache._dict.keys(): + for pkg in self.cache: for f in self._filters: - if f.apply(self.cache._dict[pkg]): - self._filtered[pkg] = 1 + if f.apply(pkg): + self._filtered[pkg.name] = 1 break def setFilter(self, filter): diff --git a/debian/changelog b/debian/changelog index 261ff7bd..6cbdaac7 100644 --- a/debian/changelog +++ b/debian/changelog @@ -5,8 +5,10 @@ python-apt (0.7.11) UNRELEASED; urgency=low * Replace support for file objects with a more generic support for any object providing a fileno() method and for file descriptors (integers). * Add support for the Breaks fields + * Only create Package objects when they are requested, do not keep them in + a dict. Saves 10MB for 25,000 packages on my machine. - -- Julian Andres Klode <jak@debian.org> Mon, 13 Apr 2009 18:08:10 +0200 + -- Julian Andres Klode <jak@debian.org> Wed, 15 Apr 2009 13:47:42 +0200 python-apt (0.7.10.3) unstable; urgency=low |
