[bcn-pm] arxius amb registres d'amplada coneguda

MINUJA MINUJA at teleline.es
Fri Sep 5 09:16:12 CDT 2003


Moltes gracies Xavier. Ara he començat a llegir un llibre que he trobat 
en una biblioteca que es diu "Javascript, CGI y Perl" i que sembla que 
promet. A part veig que ara als quiosc ha sortit un coleccionable de 12 
fascicles titulat "PROGRAMACION EN LINUX" que em pregunto si pot estar 
be per entrar una mica mes en materia.

Salutacions.

Miquel.


----- Mensaje Original -----
De: Xavier Noria <fxn at hashref.com>
Fecha: Jueves, Septiembre 4, 2003 11:50 pm
Asunto: [bcn-pm] arxius amb registres d'amplada coneguda

> En Miquel va demanar a l'anterior reunio per una manera rapida de 
> llegir 
> un registre en un arxiu en el qual tots els registres tenen la 
> mateixa 
> longitut i camps d'amplada fixa i coneguda.
> 
> Varem comentar que seek() i read() podrien servir pero que ho 
> parlariem 
> a la llista, aixi que envio un codi que il.lustra el tema.
> 
> Si fem anar el salt de linia com a separador de registres, o si es 
> un 
> altre pero els camps mateixos poden dur salts de linia, tal com 
> varen 
> dir a la reunio cal que treballem sempre en mode binari, tant per 
> a 
> escriure com per a llegir.
> 
> Aixo es aixi perque encara que print() i read() s'ho fan per a que 
> en el 
> codi un salt de linia sempre sigui eq "\n" en qualsevol plataforma 
> si es 
> treballa en mode text, resulta que seek() no te en compte aquest 
> tema i 
> no hi ha manera portable de saltar d'una tacada a l'inici del 
> registre 
> que volem llegir.
> 
> Com a curiositat, hi ha comentada una alternativa a read() que fa 
> anar 
> un cas especial d'assignacio a $/.
> 
> -- fxn
> 
> El suposat fitxer foo.dat s'enten que conte registres del tipus
> 
> aaaBBBBccc
> dddEEEEfff
> gggHHHHiii
> etc.
> 
> de tres camps cadascuna, i que ha estat creat en mode binari.
> 
> #!/usr/bin/perl
> 
> use strict;
> use warnings;
> 
> use Fcntl ':seek';
> 
> # Longitut d'un registre, sense comptar el separador de registres.
> use constant RECORD_SIZE => 10; # bytes
> 
> # Longitut del separador de registres. Si fem anar "\n" tenint l'arxiu
> # en mode binari a l'escriure i llegir aquest 1 es portable.
> use constant RECORD_SEP_SIZE => 1; # bytes
> 
> # Plantilla per a unpack().
> #
> # A l'exemple hi ha tres camps a cada registre, un de 3 bytes, l'altre
> # de 4, i l'ultim de 3. Ha de sumar el mateix que RECORD_SIZE.
> use constant PACK_TEMPLATE => 'A3A4A3';
> 
> # Passem el registre que volem llegir com a argument. Prenem com a
> # conveni que el primer es el 0.
> my $record_to_read = shift;
> 
> # Obrim el fitxer amb les dades.
> open DAT, 'foo.dat' or die $!;
> 
> # I abans de res el posem en mode binari.
> binmode DAT;
> 
> # Movem el cursor al principi del registre que es vol llegir (veure
> # perldoc -f seek).
> seek DAT, $record_to_read*(RECORD_SIZE + RECORD_SEP_SIZE), SEEK_SET;
> 
> # Un cop estem en el lloc, llegim els bytes que calen.
> my $record;
> read DAT, $record, RECORD_SIZE;
> 
> # Aixo tambe es podria fer modificant $/ si volguessim, com a
> # my $record = do { local $/ = \RECORD_SIZE; <DAT> };
> 
> # Amb unpack() podem recuperar els camps d'amplada coneguda de manera
> # eficient.
> my @fields = unpack PACK_TEMPLATE, $record;
> 
> # Aixo imprimeix el segon camp, el que te quatre caracters.
> print $fields[1];
> 
> _______________________________________________
> llista dels Barcelona-pm
> Barcelona-pm at mail.pm.org
> http://mail.pm.org/mailman/listinfo/barcelona-pm
> BCN Perl Mongers: http://barcelona.pm.org
> 





More information about the Barcelona-pm mailing list