2012-02-15 7 views
1

Je suis assez nouveau avec Perl et espérais que quelqu'un puisse m'aider avec ce problème. J'ai besoin d'extraire deux colonnes d'un fichier CSV. Voici comment le format ressemble:Comment extraire plusieurs colonnes d'un fichier CSV en utilisant Perl

"ID","URL","DATE","XXID","DATE-LONGFORMAT" 

je dois extraire la colonne DATE, la colonne XXID, et la colonne immédiatement après XXID. Notez que chaque ligne ne suit pas nécessairement le même nombre de colonnes.

La colonne XXID contient un préfixe de 2 lettres et ne commence pas toujours par la même lettre. Il peut être pratiquement n'importe quelle lettre de l'aplhabet. La longueur est toujours la même.

Enfin, une fois ces trois colonnes extraites, j'ai besoin de trier sur la colonne XXID et de compter les doublons.

Répondre

0

Vous voulez certainement utiliser une bibliothèque CPAN pour analyser le CSV, car vous ne prendrez jamais en compte tous les caprices du format.

S'il vous plaît voir: How can I parse quoted CSV in Perl with a regex?

S'il vous plaît voir: How do I efficiently parse a CSV file in Perl?

Cependant, voici une solution très naïve et non idiomatiques pour cette chaîne particulière que vous avez fourni:

use strict; 
use warnings; 

my $string = '"ID","URL","DATE","XXID","DATE-LONGFORMAT"'; 

my @words =(); 
my $word = ""; 
my $quotec = '"'; 
my $quoted = 0; 

foreach my $c (split //, $string) 
{ 
    if ($quoted) 
    { 
    if ($c eq $quotec) 
    { 
     $quoted = 0; 
     push @words, $word; 
     $word = ""; 
    } 
    else 
    { 
     $word .= $c; 
    } 
    } 
    elsif ($c eq $quotec) 
    { 
    $quoted = 1; 
    } 
} 

for (my $i = 0; $i < scalar @words; ++$i) 
{ 
    print "column " . ($i + 1) . " = $words[$i]\n"; 
} 
3

Voici un exemple de script en utilisant le module Text::CSV pour analyser vos données CSV. Consultez la documentation du module pour trouver les paramètres appropriés pour vos données.

#!/usr/bin/perl 
use strict; 
use warnings; 
use Text::CSV; 

my $csv = Text::CSV->new({ binary => 1 }); 

while (my $row = $csv->getline(*DATA)) { 
    print "Date: $row->[2]\n"; 
    print "Col#1: $row->[3]\n"; 
    print "Col#2: $row->[4]\n"; 
} 
3

I a publié un module appelé Tie::Array::CSV qui permet de Perl d'interagir avec votre CSV comme un tableau Perl natif imbriqué. Si vous l'utilisez, vous pouvez utiliser votre logique de recherche et l'appliquer comme si vos données se trouvaient déjà dans un tableau de références-tableaux. Regarde!

#!/usr/bin/env perl 

use strict; 
use warnings; 

use File::Temp; 
use Tie::Array::CSV; 
use List::MoreUtils qw/first_index/; 
use Data::Dumper; 

# this builds a temporary file from DATA 
# normally you would just make $file the filename 
my $file = File::Temp->new; 
print $file <DATA>; 
######### 

tie my @csv, 'Tie::Array::CSV', $file; 

#find column from data in first row 
my $colnum = first_index { /^\w.{6}$/ } @{$csv[0]}; 
print "Using column: $colnum\n"; 

#extract that column 
my @column = map { $csv[$_][$colnum] } (0..$#csv); 

#build a hash of repetitions 
my %reps; 
$reps{$_}++ for @column; 

print Dumper \%reps; 
Questions connexes