Schnelle / effiziente Zählung der Liste der raumbegrenzten Strings in Python

Angesichts der Eingabe:

x = ['foo bar', 'bar blah', 'black sheep'] 

Ich könnte dies tun, um die Zählung jedes Wortes in der Liste der raumbegrenzten Zeichenfolge zu erhalten:

 from itertools import chain from collections import Counter c = Counter(chain(*map(str.split, x))) 

Oder ich konnte einfach durchführen und bekommen:

 c = Counter() for sent in x: for word in sent.split(): c[word]+=1 

[aus]:

 Counter({'bar': 2, 'sheep': 1, 'blah': 1, 'foo': 1, 'black': 1}) 

Die Frage ist, was ist effizienter, wenn die Eingabeliste der Zeichenfolge ist extrem riesig? Gibt es andere Möglichkeiten, das gleiche Gegenobjekt zu erreichen?

Stellen Sie sich vor, es ist ein Text-Datei-Objekt, das Milliarden von Zeilen mit jeweils 10-20 Worten hat.

  • Holen Sie sich Key Count von OrderedDict, wo Key ein Tupel ist
  • Summe aller zählt in einem Sammlungen.Counter
  • Überraschende Ergebnisse mit Python timeit: Counter () vs defaultdict () vs dict ()
  • Python Count up & Down Schleife
  • Summing Liste der Zähler in Python
  • Warum ist Collections.counter so langsam?
  • 2 Solutions collect form web for “Schnelle / effiziente Zählung der Liste der raumbegrenzten Strings in Python”

    Angenommen, Sie sind in Python 3x, sowohl chain(*map(str.split, x)) und einfache Iteration erstellen Zwischenlisten sequentiell aus jeder Zeile; Das wird in keinem Fall viel Gedächtnis in Anspruch nehmen. Leistung sollte sehr nah sein und kann implementierungsabhängig sein.

    Allerdings ist es am effizientesten Speicher, um eine Generatorfunktion zu erzeugen, um Counter () zu speisen. In jedem Fall verwenden Sie string.split (), es erstellt Zwischenlisten, die nicht notwendig sind. Dies könnte zu Verlangsamung führen, wenn Sie eine besonders lange Linie haben, aber um ehrlich zu sein, ist es unwahrscheinlich.

    Eine solche Generatorfunktion wird nachfolgend beschrieben. Beachten Sie, dass ich die optionale Eingabe für Klarheit verwende.

     from typing import Iterable, Generator def gen_words(strings: Iterable[str]) -> Generator[str]: for string in strings: start = 0 for i, char in enumerate(string): if char == ' ': if start != i: yield string[start:i] start = i if start != i: yield string[start:i] c = counter(gen_words(strings)) 

    Die Antwort auf Ihre Frage ist Profiling .

    Im Folgenden sind einige Profiling-Tools:

    • Drucken time.time () an strategischen Orten. (Oder Unix-Zeit verwenden )
    • CProfile
    • Line_profiler
    • Heapy verfolgt alle Objekte in Pythons Erinnerung (gut für Speicherlecks)
    • Für lang laufende Systeme, verwenden Sie dowser : ermöglicht Live-Objekte introspection (Web-Browser-Schnittstelle)
    • Memory_profiler für RAM-Nutzung
    • Untersuche Python-Bytecode mit dis
    Python ist die beste Programmiersprache der Welt.