Python re-Modul Cache-Clearing

8

Beim Lesen der Dokumentation zu Python re habe ich mich entschieden, einen Blick auf re.py Quellcode zu werfen.

Als ich es öffnete, fand ich folgendes:

%Vor%

Warum wird der Cache mit _cache.clear() gelöscht, wenn er _MAXCACHE der Einträge erreicht?

Ist es üblich, den Cache vollständig zu löschen und von vorne anzufangen?

Warum gerade nicht am längsten benutzt, wird der eingelöste Wert gelöscht?

    
ovgolovin 22.09.2011, 19:52
quelle

3 Antworten

3

Wenn ich raten müsste, würde ich sagen, dass es so gemacht wurde, um nicht zu verfolgen, wann / wie lange einzelne Werte im Cache gespeichert wurden, was sowohl Speicher- als auch Verarbeitungsaufwand verursachen würde. Da das verwendete Caching-Objekt ein Dictionary ist, das inhärent ungeordnet ist, gibt es keine gute Möglichkeit zu wissen, welche Order Items ohne ein anderes Caching-Objekt hinzugefügt wurden. Dies könnte behoben werden, indem ein OrderedDict anstelle eines Standardwörterbuchs verwendet wird, vorausgesetzt, Sie arbeiten mit Python & gt; = 2.7, aber ansonsten müssten Sie die Art und Weise, wie das Caching implementiert wurde, grundlegend neu gestalten a clear() .

    
g.d.d.c 22.09.2011, 20:22
quelle
5

Hier ist ein Zitat von einem der Entwickler eines neuen regex -Moduls, das für 3.3 im Hinblick auf das Caching geplant ist. Dies ist Teil einer Liste von Features, die das neue Modul vom aktuellen re -Modul trennt.

  

7) Ändern Sie den neu kompilierten Ausdruckcache, um den   Verdrängungszustand. Derzeit, wenn reguläre Ausdrücke kompiliert werden,   Das Ergebnis wird zwischengespeichert, sodass, wenn derselbe Ausdruck erneut kompiliert wird,   Es wird aus dem Cache abgerufen und es muss keine zusätzliche Arbeit geleistet werden. Dies   Cache unterstützt bis zu 100 Einträge. Sobald der 100. Eintrag erreicht ist, wird der   Cache wird gelöscht und eine neue Kompilierung muss stattfinden. Die Gefahr, alles sei gut   selten, ist, dass man den 100. Ausdruck kompilieren kann, nur um diesen zu finden   kompiliert es neu und muss, wenn es möglich ist, die gleiche Arbeit wiederholen   wurden 3 Ausdrücke vor getan. Indem Sie diese Logik leicht modifizieren   Es ist möglich, einen beliebigen Zähler zu erstellen, der einen Zeitstempel gibt   jeder kompilierte Eintrag und anstatt den gesamten Cache zu löschen, wenn es   erreicht Kapazität, nur die älteste Hälfte des Caches beseitigen, halten   die Hälfte, die jünger ist. Dies sollte die Möglichkeit von   sich auf Fälle einlassen, in denen eine sehr große Anzahl von regulären Ausdrücken vorhanden ist   ständig neu kompiliert. Zusätzlich werde ich das Limit auf aktualisieren   256 Einträge, was bedeutet, dass die 128 neuesten beibehalten werden.

Ссылка

Dies deutet darauf hin, dass es eher die Faulheit des Entwicklers oder "eine Betonung der Lesbarkeit" ist, die das aktuelle Caching-Verhalten erklärt.

    
Andrew Clark 22.09.2011 21:14
quelle
1

Der Caching-Punkt dient dazu, die durchschnittliche Anrufzeit der Funktion zu verringern. Der Overhead, der damit verbunden ist, mehr Informationen in _cache zu behalten und ihn zu beschneiden, anstatt ihn zu löschen, würde die durchschnittliche Anrufzeit erhöhen. Der _cache.clear() -Aufruf wird schnell abgeschlossen, und obwohl Sie Ihren Cache verlieren, ist dies vorzuziehen, einen Cache-Status beizubehalten und den Aufwand zu haben, einzelne Elemente aus dem Cache zu entfernen, wenn das Limit erreicht ist.

Es gibt einige Dinge, über die Sie bei der Berechnung der Cache-Effizienz nachdenken sollten:

  1. Durchschnittliche Anrufdauer bei Cachetreffern (sehr kurz)
  2. Durchschnittliche Anrufzeit bei Cache-Misses (länger)
  3. Häufigkeit der Cachetreffer (ziemlich ungewöhnlich)
  4. Anrufzeit, wenn der Cache gelöscht oder beschnitten wurde (ziemlich ungewöhnlich)

Die Frage ist, dass # 3 Sinn macht, wenn es auch bedeutet, # 2 und # 4 zu erhöhen. Meine Vermutung ist, dass es nicht, oder der Unterschied ist vernachlässigbar genug, dass die Einhaltung des Codes vorzuziehen ist.

    
Andrew Clark 22.09.2011 20:29
quelle

Tags und Links