10 Stimmen

Wie kann ich in Perl Zeilen vom Ende einer Datei lesen?

Ich arbeite an einem Perl-Skript, um eine CSV-Datei zu lesen und einige Berechnungen durchzuführen. CSV-Datei hat nur zwei Spalten, etwa wie unten.

One Two
1.00 44.000
3.00 55.000

Diese CSV-Datei ist sehr groß, sie kann zwischen 10 MB und 2 GB groß sein.

Derzeit nehme ich eine CSV-Datei mit einer Größe von 700 MB. Ich habe versucht, diese Datei in Notepad und Excel zu öffnen, aber es sieht so aus, als würde keine Software sie öffnen.

Ich möchte vielleicht die letzten 1000 Zeilen aus der CSV-Datei lesen und die Werte sehen. Wie kann ich das tun? Ich kann die Datei nicht in Notepad oder einem anderen Programm öffnen.

Wenn ich ein Perl-Skript schreibe, muss ich die gesamte Datei verarbeiten, bis zum Ende der Datei gehen und dann die letzten 1000 Zeilen lesen.

Gibt es einen besseren Weg dorthin? Ich bin neu in Perl und bin für jeden Vorschlag dankbar.

Ich habe das Netz durchsucht und es gibt einige Skripte wie File::Tail aber ich weiß nicht, ob sie unter Windows funktionieren?

2voto

geocar Punkte 8805
perl -n -e "shift @d if (@d >= 1000); push(@d, $_); END { print @d }" < bigfile.csv

Obwohl eigentlich die Tatsache, dass UNIX-Systeme einfach tail -n 1000 sollte Sie davon überzeugen, einfach zu installieren cygwin o colinux

1voto

Adam Lerman Punkte 3329

Ich glaube, Sie können das Tie::File-Modul verwenden. Es sieht aus wie dies lädt die Zeilen in ein Array, dann könnten Sie die Größe des Arrays und verarbeiten arrayS-ze-1000 bis arraySize-1.

Krawatte::Datei

Eine andere Möglichkeit wäre, die Anzahl der Zeilen in der Datei zu zählen, dann eine Schleife durch die Datei zu ziehen und mit dem Einlesen der Werte bei numberofLines-1000 zu beginnen

$count = `wc -l < $file`;
die "wc failed: $?" if $?;
chomp($count);

Damit erhalten Sie die Anzahl der Zeilen (auf den meisten Systemen.

0voto

David Nehme Punkte 21073

Wenn Sie die Anzahl der Zeilen in der Datei kennen, können Sie Folgendes tun

perl -ne "print if ($. > N);" filename.csv

wobei N gleich $num_lines_in_file - $num_lines_to_print ist. Sie können die Zeilen zählen mit

perl -e "while (<>) {} print $.;" filename.csv

0voto

Littlelegs Punkte 9

Die Module sind der richtige Weg. Es kann jedoch vorkommen, dass Sie einen Code schreiben, der auf einer Vielzahl von Rechnern laufen soll, denen die obskuren CPAN-Module fehlen. Warum dann nicht einfach "tail" verwenden und die Ausgabe in eine temporäre Datei aus Perl heraus ausgeben?

#!/usr/bin/perl

`tail --lines=1000 /path/myfile.txt > tempfile.txt`

Sie haben dann etwas, das nicht von einem CPAN-Modul abhängig ist, falls die Installation eines solchen Moduls ein Problem darstellen könnte.

-1voto

dlamblin Punkte 42420

Ohne sich auf tail zu verlassen, was ich wahrscheinlich tun würde, wenn Sie mehr als $FILESIZE [2GB?] Speicher haben, würde ich einfach faul sein und es tun:

my @lines = <>;
my @lastKlines = @lines[-1000,-1];

Auch wenn die anderen Antworten, die Schwanz o seek() sind so ziemlich der beste Weg, um dies zu erreichen.

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X