/blog/perl


substr() in Perl
[127001 mal gelesen]
foreach in Perl
[116149 mal gelesen]
Arrays in Perl - Besonderheiten
[109128 mal gelesen]
open() - Dateien öffnen in Perl
[97739 mal gelesen]
split() in Perl - Zeichenketten teilen
[88645 mal gelesen]
chomp() in Perl
[84410 mal gelesen]
grep - Listen durchsuchen in Perl
[81727 mal gelesen]
push in Perl
[78538 mal gelesen]
sleep in Perl - Das aktuelle Script warten lassen
[61110 mal gelesen]
print in Perl
[49722 mal gelesen]


Arrays
Dateien
HTPC
Hashes
Leistungsoptimiert
PHP
Perl
RegEx
Schleifen
Script
Skalare
Sonstiges
System
Webserver
Zur Startseite


Mittwoch, 9.1.2008, 21:59:18 Uhr

Wie viele Zeilen hat die Datei?


So ne kleinere Spielerei nebenbei, aber auch hübsch, um zu sehen, was Perl so kann: Wie viele zeilen hat eine Datei?

Man will also wissen, wie viele Zeilen in einer Datei stehen, gesucht wird eine möglichst effektive und Speicherschonende Möglichkeit, dies herauszufinden.

Variante 1: Datei einlesen und zählen
Man liest also die Datei komplett ein und läßt die zeilen zählen, etwa so

open (my $in,'<','test.txt');
@zeilen= <$in>;
close $in;

$zeilenanzahl=@zeilen;
print "Die Datei hat $zeilen Zeilen";



Ja, das geht, aber: Wenn die Datei mehrere Megabyte oder sogar Gigabyte hat, wirds dem Rechner ein bißchen viel...
Die ganze Datei einlesen ist also schon mal blöd.

Ha, Idee, Zeilen nacheinander einlesen:


$zeilen=0;
open (my $in,'<','test.txt');
while (<$in>){$zeilen++;}
close $in;

$zeilenanzahl=@zeilen;
print "Die Datei hat $zeilen Zeilen";



Bingo, geht auch und liest nur einzelne Zeilen ein. Aber Vorsicht: Wenn eine Zeile mehrere MB oder gar GB hat, wirds dem Rechner auch wieder ein bißchen viel, denn pro Zeile wird die aktuelle Zeile $_ zugeordnet, also eingelesen!

Also schon schön, aber nicht perfekt...

Besser gehts so:


open (my $in,'<','test.txt');

$cou += tr/\n/\n/ while read ($in,$_,1024000);

close $in;
print "Die Datei hat $cou Zeilen";


Was passiert hier?
Die Datei wird geöffnet.

Danach wir per read jeweils ein Datenblock von einem Megabyte in $_ eingelesen und die darin enthaltenen \n's gezählt (tr /\n/\n/) und $cou hinzugefügt.

Wieso ist das nun besser?
Weil immer nur maximal ein MB Daten eingelesen werden. Auf Wunsch kann man den Puffer natürlich verkleinern oder vergrößern...


Man sollte es immer vermeiden, Dateien komplett einzulesen, wenn es geht. Sehr lange Dateien können, wenn sie in den Rechnerspeicher eingelesen werden, den Rechner so ziemlich lahm legen!

In diesem Sinne, bis zum nächsten Mal...





Kommentare zum Beitrag "Wie viele Zeilen hat die Datei?"

Kommentar von Renée Bäcker
Wenn es nur um das "Zählen" mit tr/// geht, kannst Du den Ersetzungsteil leer lassen, also

tr/\n//

Solange keine Modifier (tr/\n//cd o.ä.) angegeben werden, wird nichts ersetzt sondern nur gezählt. So geräts Du nicht in Gefahr, durch einen Tippfehler alles zu ersetzen (tr/\n/n/).

Kommentar von Struppi
Warum nicht einfach:

open FH, "test.txt";
while(<FH>){}
print "Zeilen $.";
close FH;


Kommentar von Admin
Nunja, wie ich oben bereits geschrieben habe, wird auch bei
while (<in>){}
die Datei komplett in den Speicher eingelesen. Zwar zeilenweise, aber was, wenn eine Zeile mal 'nen GB hat?
Und um das nachzuvollziehen, kann man ja mal 'ne 1 GB-Datei anlegen, wobei das eine GB in nur einer Zeile steht, also ohne breaks.
Diese eine Zeile liest man dann mal ein... und geht dann Kaffee kochen. Also bei mir hier dauerte es mehrere Minuten, bis sich Perl wieder zurückmeldete, der Systemspeicher ging unterwegs auf 10 MB herunter... in einem 2 GB-System mit Windows. Dabei ging die Prozessorauslastung auf 70 % hoch und die Festplatte lief sich tot... nun, so gehts jedenfalls nicht, da man nie weiss, was man so einlesen muß.

Im Gegensatz dazu brauchte "meine" Methode 3 Sekunden und der Rechner blieb cool. Besser, denke ich...

Kommentar von Struppi
Na gut, wenn du GB grosse Dateien ohne Newline Zeichen hast, dann ist das sicher richtig (wobei das Problem nicht an Perl liegt, sondern am OS). Bei mir kommen solche Dateien selten vor (im Grunde nie).

Realistischer ist z.b. das man die Anzahl der Zeilen in einem Logfile herausfinden möchte, also extrem viele Zeilen mit ca. 100 Zeichen.

Jetzt mach mal einen Benchmark, deine Lösung braucht bei 100.000 Zeilen braucht bei mir sechsmal so lange und je mehr Zeilen umso schlechter wird das Verhältnis.

Also man sollte sich vorher überlegen, ob man Dateien hat, die extrem lange Zeilen haben könnten, dann wäre deine Lösung optimal, bei normal langen Zeilen ist sie langsam.

Kommentar von Peter
finde den Blog gut, habe aber einen Fehler entdeckt in
"Wie viele Zeilen hat die Datei"

Statt:
$zeilenanzahl=@zeilen;
print "Die Datei hat $zeilen Zeilen";
muss es heißen:
$zeilenanzahl=@zeilen;
print "Die Datei hat $zeilenzahl Zeilen";



Thema: Perl

Der Beitrag "Wie viele Zeilen hat die Datei?" wurde 9653 mal gelesen.

Kommentar schreiben  Druckansicht  Seitenanfang 
Beurteilen 






 Zufällige Beiträge im /blog/perl

Prüfen ob Variable belegt ist - defined in Perl

Permanent redirect 301 - Wie leite ich eine Seite um?

Eine Datei zeilenweise einlesen mit Perl

Dateien öffnen mit Fehlerabfrage

abs() in Perl - Absolutwert einer Zahl ermitteln

exists() - Prüfen, ob ein Hash-Element existiert

HTML-Code ausgeben mit Perl

Dateiendung herausfinden mit Perl

abs() in Perl

RegEx Spickzettel - Abkürzungen in regulären Ausdrücken



0.0376009941101074 sec. to build



...Blogsoftware in pure Perl - Powered by a lot of Coffee...


SSD-Festplatte - Wassn das???
Die Transliteration - Nur ein Zeichen in einem Skalar ersetzen
Select - Case in Perl
Windows 7 XP Mode – Wo finde ich den XP-Modus unter Windows 7?
Mac-Adresse beim Apple Macintosh herausfinden
SGN-Funktion für Perl
truncate - Dateigröße verändern in Perl
Eigene IP herausfinden mit Perl
Epoche live in Datum umwandeln
Firefox 3 - Exe-Files downloaden


Von: Fabian
Kommentar:
Hallo zusammen,
ich suche schon etwas im Internet und bin bisher nicht fündig geworden.
Zum Beitrag


Von: Schorschel eastcoast
Kommentar:
Danke. Das hat mir weitergeholfen.
Zum Beitrag


Von: Jessica
Kommentar:
Kann man auch zwei Datein parallel einlesen?

Zum Beitrag


Von: Xtravaganz
Kommentar:
Für

Zum Beitrag


Von: Xtravaganz
Kommentar:
Für

Zum Beitrag



Gesamtverzeichnis
Februar 2010
Dezember 2009
Oktober 2009
Januar 2009
Dezember 2008
November 2008
September 2008
August 2008
Juli 2008
Juni 2008
Mai 2008
April 2008
Januar 2008
Dezember 2007
November 2007
Oktober 2007
September 2007
August 2007
Juni 2007
Mai 2007
April 2007
März 2007
Februar 2007
Januar 2007
Dezember 2006


Mister Wong

RSS-Feed

Heute ist der
22.7.2018

Es ist
8:35:51 Uhr

Ihre IP:
54.198.77.35

Blog-Einträge: 186

Die letzten 24 Stunden im Überblick


Gelesene Beiträge insgesamt:
3687050


Webseiten vergleichen
Kalender mit Feiertagen - 2028
Links finden und testen
Menschliche Datumsangaben
IP zu Domain herausfinden
Time live in Datum umwandeln
Perl für Windows



Mo Di Mi Do Fr Sa So
1
2345678
9101112131415
16171819202122
23242526272829
3031

Impressum