Les 3 qualités du programmeur Paresse Impatience Orgueil —...
Transcript of Les 3 qualités du programmeur Paresse Impatience Orgueil —...
Formation Perl
Les 3 qualités du programmeur
● Paresse● Impatience● Orgueil
— Larry Wall
2
Formation Perl
Les 3 qualités du programmeur
● Paresse : écrire moins de code● Impatience : aller rapidement au but● Orgueil : pousse à écrire de bons programmes
→ Perl
3
Formation Perl
Exemple :
String a = "Bonjour, vaste Monde !";Pattern p = Pattern.compile("([az]+?) ");Matcher m = p.matcher(a);if (m.find()) { System.out.print(m.group(1));}
4
Formation Perl
Exemple :
$_ = "Bonjour, vaste Monde !";print $1 if /([az]+?) /;
5
Formation Perl
Les types de variables : scalar
$chaine = "123\n";$chaine = '123'; # attention '123\n'$nombre = 123.45;
print $nombre + 1; # 124.45print $chaine + 1; # 124
$piege = "123,45";print $piege + 1; # 124$piege =~s/,/./;print $piege + 1; # 124.45
print uc($chaine); # ?
6
Formation Perl
Les types de variables : array
@liste = (1, 2, 'foo', 'bar');@liste = qw( 1 2 foo bar ); # Perl++print $liste[0];print $liste[9]; # rienprint scalar(@liste);print $#liste;print @liste; # attention : 12foobarprint "@liste";print "Liste de ".@liste." éléments";
7
Formation Perl
Les types de variables : hash
%dictionnaire = ('foo' => 123, 'bar' => 456);print $dictionnaire{'foo'};print $dictionnaire{'baz'}; # rienprint scalar(keys %dictionnaire);
print %dictionnaire; # attention : bar456foo123foreach (keys %dictionnaire) {
print "$_ => $dictionnaire{$_}\n";}
foreach (sort keys %dictionnaire) …foreach (sort {$b cmp $a} keys %dictionnaire) …
foreach (sort {$dict{$a} cmp $dict{$b}} keys %dict) …
8
Formation Perl
Les variables spéciales
$_ = "foobar";s/oo/u/;
local $\ = "\n";@liste = (1,2,3);foreach $element (@liste) {
print $element; # « println »}
# Perl 5.10+ (depuis 2008)use feature ":5.10";say $element;
local $/; # ?
9
Formation Perl
Les variables spéciales
local $/;open $fichier, "fichier.txt";$_ = <$fichier>;print s/\n//g;
# wc l fichier.txt
@ARGV%ENV$!…
# man perlvar# perldoc perlvar (sous Windows)
10
Formation Perl
defined, undef, delete, …
%d = ('foo' => 'a', 'bar' => 'b', 'baz' => 'c');
delete $d{'bar'};
undef $d{'foo'};$d{'foo'} = undef; # idem
foreach (keys %d) { print "$_ => $d{$_}\n" }
print "defined" if (defined $d{'foo'});print "exists" if (exists $d{'foo'});print "true" if ($d{'foo'});
11
Formation Perl
Manipulation de listes
@a = qw(Aujourd'hui est un grand jour);
print @a[0,2];print @a[$#a 1 .. $#a];
push(@a, 'radieux');$dernier = pop(@a);$premier = shift(@a);unshift(@a, 'Ce', 'jour');splice(@a, 0, 2, "Demain", "sera", "aussi");splice(@a, 2, 1, 'autre');# (splice renvoie la liste des éléments retirés)
while (($cle, $valeur) = each @a) {print "$cle => $valeur\n";
}
12
Formation Perl
Manipulation de listes
@liste = (1, 4, 3, 2);@liste = sort @liste;@decroissant = sort {$b <=> $a} @liste;
@liste = qw( Foo bar Baz );@az = sort @liste;@za = sort {uc($b) cmp uc($a) } @liste;
print join(" et ", @liste);print reverse(@liste);@contiennent_a = grep(/a/, @liste);@liste = map { uc($_) } @liste;# for (@liste) { push @b, uc($_) }; @liste = @b; undef @b;
13
Formation Perl
Manipulation de listes
@a = (1, 4, 3, 2);
@b = @a;
$b[0] = 'foo';print "@b\n";
print "@a";
14
Formation Perl
Manipulation de dictionnaires
%h = ('a' => 'foo', 'b' => 'bar');
while (($cle, $valeur) = each %h) {print "$cle => $valeur\n";
}
for (($cle, $valeur) = each %h) # non !
for (values %h) { s/foo/baz/ } # attentionprint %h;
%h = map { uc($_) => $h{$_} } keys %h;
15
Formation Perl
Tests
if (1 && 'quelque chose') …if (1 || 0) …
if ($chose) {print 'chose ok';
} elsif (!$truc) {print 'pas truc';
} else {print 'autre cas';
}
print 'ok' if $abc;print 'non' unless $machin;
$abc and print 'ok';$bidule or print '$bidule est faux';
16
Formation Perl
Tests
if (%d) … # nonvide ()if (@d) … # nonvide ()if ($d) … # ni 0 ni '' ni undef
@d = ('', '', '');if (!@d) {
print 'Que du vide ?';}
17
Formation Perl
Tests
switch() case …
# Perl 5.10+use feature ":5.10";given($a) { when(1) { print "un"; } when(2) { print "deux"; } default { print "je ne sais pas"; }}
18
Formation Perl
Tests
if ($abc == 123) …if ($abc != 123) …if ($abc > 123) …if ($abc >= 123) …if ($abc <= 123) …print $abc <=> 123;
if ($bcd eq "Mot") …if ($bcd ne "Mot") …if ($bcd gt "Mot") … # use locale !if ($bcd lt "Mot") …if ($bcd ge "Mot") …if ($bcd le "Mot") …print $bcd cmp "Mot";
19
Formation Perl
Tests
$abc = $bcd // 'par défaut'; # rare$abc = defined($bcd) ? $bcd : 'par défaut';$abc = $bcd // $cde // $def // 'rien';
@b = (1,2,3); @c = (4,5);if (@b || @c) {
print "Au moins une des listes n'est pas vide.";}
@a = @b || @c; # attention
20
Boucles
foreach (@liste) …
for (@liste) {print "un élément de la liste : $_ \n";
}
for ($i=0; $i < 10; $i++)for $i (0..10) # attention
for ('001' .. '100') # pas besoin de sprintffor ('abc' .. 'zzz')
for (1 ... 10) # rare (man perlop)
Formation Perl
21
Boucles
while ($i < 10) {…
}
do {…
} while $i < 10;
$i = 0;while ($i < 10) {
next if $i % 2;print "$i\n";
} continue { # on y passe à chaque itération$i++; # même en cas de next
}
Formation Perl
22
Boucles
do {…
} until $i > 10;
$i = 0;do {
$i++;next if $i % 2;print "$i\n";
} until $i > 10;
# hélas : Can't "next" outside a loop block# un bloc do { … } n'est pas une boucle# mais un bloc { … } est une boucle (une fois)# donc …
Formation Perl
23
Boucles
$i = 0;do {{
$i++;next if $i % 2;print "$i\n";
}} until $i > 10;
# hmmm …
Formation Perl
24
Boucles
while ($i < 10) {last if $i == 8;$i++;print "$i\n";
}
# mais, comme pour do { next … } until … :do {
last if $i == 8;$i++;print "$i\n";
} until $i > 10;# Can't "last" outside a loop block# donc …
Formation Perl
25
Boucles
{ do {
last if $i == 8;$i++;print "$i\n";
} until $i > 10;}
# man perlsyn
Formation Perl
26
Boucles
@a = qw(il y a une cé sure dans cette phrase);
$i = 1;
while ($mot = shift @a) { print $i++." "; if ($mot=~s/$//) {
$mot .= shift @a; redo;
}print "$mot\n";
}
Formation Perl
27
Boucles avec étiquette
BOUCLE_I: for $i (0..5) { for $j (0..9) {
print "$i$j\n"; next BOUCLE_I if $i % 2 && $j > 1;
} }
# idem pour last et redo# man perlsyn
Formation Perl
28
Listes de listes, Dictionnaires de listes, …
@a = ([1, 2], [3, 4, 5, 6], [7, 8, 9]);print $a[1][2];
%h = ('foo' => ['a', 'b', 'c'], 'bar' => [1, 2]);print $h{'foo'}[2];
@a = ({'foo' => 'bar'}, {'baz' => 123});print $a[0]{'foo'};
%h = ('foo' => {'a' => [123, 456, 78], 'b' => 321 });print $h{'foo'}{'a'}[1];
# pourquoi pas @a = ((1,2), (3,4,5,6), (7,8,9)) ?# pourquoi pas @a = (('foo' => 'bar'), … ?
Formation Perl
29
Listes de listes, Dictionnaires de listes, …
@a = (1, 2, 3);
$aref = [1, 2, 3];
print @$aref[1]; # ouch !print ${$aref}[1]; # pas mieux … print $aref>[1];
%h = ('foo' => 'bar', 'baz' => 123);
$href = {'foo' => 'bar', 'baz' => 123};
print ${$href}{'foo'}; # hmmm …print $href>{'foo'};
print keys %$href;print keys %{$href};
Formation Perl
30
Listes de listes, Dictionnaires de listes, …
@a = (1, 2, 3);
$aref = \@a;
%h = ('foo' => 'bar', 'baz' => 123);
$href = \%h;
# et d'ailleurs … $s = 'essai';$sref = \$s;print $$sref;
$b = $aref;print $b>[1];$b>[0] = 'foo'; # attentionprint "@a";
Formation Perl
31
Listes de listes, Dictionnaires de listes, …
@villes = ( 'Paris FR', 'Barcelone ES','Bruxelles BE','Bordeaux FR','Tortosa ES' );
foreach (@villes) {($ville, $pays) = split;push(@{$par_pays{$pays}}, $ville);
}
while (($pays, $villes) = each %par_pays) {print "$pays : ".join(', ', @{$villes})."\n";
}
# man perldsc# man perlreftut
Formation Perl
32
Manipuler du texte
use locale;@a = qw(essai épatant autre);print sort @a;
# également pour gt lt ge le cmp
# RegExps : Regular Expressions
$abc =~/foo/ and print "trouvé !";$abc =~m/foo/ and …
$abc =~s/foo/bar/;
print $abc =~s/foo/bar/;
Formation Perl
33
Manipuler du texte
$_ = "Ceci n'est pas un match de football...";
/foot(.*)/ and print $1;/foot(.*)l/ and print $1;/foot(.*?)l/ and print $1;/f(o*)t(.*)/ and print $2;/f(?:o*)t(.*)l/ and print $1;/(fo+)/ and print $1;/(fo{2,5})/ and print $1;/(fo{2})/ and print $1;/(fo{2,})/ and print $1;/(balle?)/ and print $1;/(foo\w+)/ and print $1;/(football(eurs|euses)*)/ and print $1;/(Ce\w+a)/ and print $1;/(Ce[^u]*)/ and print $1;/(foo[^.]*)/ and print $1;
Formation Perl
34
Manipuler du texte
$_ = "Ceci n'est pas un match de football...";
/\.$/ and print "point final";/(\w+)['.]+$/ and print $1;/^[AZ]/ and print "majuscule au début";/^[aeiou]/i and print "voyelle au début, maj ou min";
$re = "(\\w+)['.]+\$"; # pas pratique$re = qr{(\w+)['.]+$};$re = qr{ (\w+) ['.]+ $ }x; # plus lisible ?/$re/ and print $1;
$re = "(?i)ceci";/$re/ and print "Ceci ou ceci ou cEcI … ";
Formation Perl
35
Guillemets, délimiteurs,...
'aujourd\'hui' q(aujourd'hui)↔"John \"Unknown\" Doe" qq(John "Unknown" Doe)↔`ls l` qx(ls l)↔/foo.*bar/ m(foo.*bar)↔"l'.*\"(\\w+)\"\\.\$" qr(l'.*"(\w+)"\.$)↔
# pas forcément des parenthèses :s/\/home\//\// # ouf...s!/home/!/!s|/home/|/|
$deux_lignes = "Ligne 1Ligne 2";
$deux_lignes = <<EOT;Ligne 1Ligne 2EOT
Formation Perl
36
Manipuler du texte
/(\w+?)\W/ and print $1;/\s(\w+)/ and print $1;/\s(\S+)/ and print $1;
$_ = "France : 3 Brésil : 0";s/(\d+)(.*?)(\d+)/\3\2\1/ and print;s/\d/1/g;s/(\w+)/uc($1)/ge and print; # use encoding 'utf8';s/ /\n/ and print;
$_ = "France : 3\nBrésil : 0";s/\d.*/1/g and print;s/\d.*/1/gs and print;s/^[AZ]/+/gms and print;
tr/france/bresil/; # ou y///
Formation Perl
37
La longue marche vers Unicode...
# Perl 5.8.0 minimum (2002)
print uc('Brésil');use encoding 'utf8'; # si BRéSIL# ou use utf8;
open($fh, '<', 'fichier.txt');binmode STDOUT, ":utf8"; # si Br sil�$_ = <$fh>;for (split(/\W/)) { print "$_\n"; }
open($fh, '<:encoding(utf8)', 'fichier.txt');# si Br sil
Formation Perl
38
La longue marche vers Unicode...
# toutes E/S en utf8 en une instruction :use open ':utf8', ':std';use open qw(:utf8 :std);
print "\x{4eba}humain\x{263a}\n";
/(\w+)/ and print $1;/(\p{Alphabetic}+)/ and print $1;/(\p{Latin}+)/ and print $1;/(\P{Latin}+)/ and print $1;…
# man perluniintro
Formation Perl
39
La longue marche vers Unicode...
use utf8;use Text::Unidecode;
$_ = "Et l'œuf se fêla, comme ça";print unidecode($_);
print unidecode("Kärntner Straße"); # Karntner Strasse
print unidecode("北亰 "); # Bei Jing
Formation Perl
40
La longue marche vers Unicode...
use encoding 'utf8';use charnames ':full';
print "Stra\N{LATIN SMALL LETTER SHARP S}e";
# http://www.fileformat.info/info/unicode/char/a.htm
Formation Perl
41
Manipuler du texte
$_ = "Ceci n'est pas un match de football...";
/foo.*l/ and print $&; # aussi $` et $'
/foo(?=t)/ and print $&;/foo(?=\w)[^\d]/ and print $&;# foo suivi d'un caractère alphanumérique mais pas numérique
/foo(?!bar).*/ and print $&;/(foo(?!bar).*?)\.{3}/ and print $1;
/(?<=foot).*/ and print $&;s/(?<=foot)[^.]*// and print;s/foot\K[^.]*// and print; # idem en raccourci
/(?!foot)ball/ and print $&; # piège !/(?<!foot)ball/ and print $&;/\S*(?<!foot)ball/ and print $&;
Formation Perl
42
Manipuler du texte
$_ = "truc123 machin 456, chose : 789";
if (/(\d+).*?(\d+).*?(\d+)/) {$truc = $1;$machin = $2;$chose = $3;
}
($truc, $machin, $chose) = ( /\d+/g );($machin, $chose) = ( / (\d+)/g );
$_ = "truc123 machin 456, parasite384 ! chose : 789";($truc, $machin, undef, $chose) = ( /\d+/g );( $truc ) = ( /\d+/g );( $truc ) = ( /truc(\d+)/ );
# perldoc perlop « Matching in list context »
Formation Perl
43
Manipuler du texte
$_ = "abc123";
# commence par des caractères alphabétiques,# qui ne sont pas suivis par 123 ?
/[az]+(?!123)/ and print "Ok c'est bon.";
# ab suivi de c, ça matche ! print $&
/[az]+(?=\d)(?!123)/ and print "Ouf !";
/[az]+(?!123)\d+/ and print "Si je peux simplifier...";
# man perlre# man perlrequick# man perlretut
Formation Perl
44
Fonctions
sub foo {print "J'entre dans la fonction foo\n";
}
foo();
sub bar {return "Résultat de la fonction bar\n";
}
print "bar retourne : ".bar()."\n";
Formation Perl
45
Fonctions
sub foo {print "J'entre dans la fonction foo avec ".
@_." arguments : ".join(", ", @_)."\n";$arg1 = shift;$arg2 = shift;# ou ($arg1, $arg2) = @_;return $arg1 + $arg2;
}
$valeur_retour = foo(4, 3);($val1, $val2) = foo(5, 9, 123);print "val1 : $val1 et val2 : $val2\n";print foo('oups', 'gaffe');
Formation Perl
46
Fonctions
sub foo($$) {print "J'entre dans la fonction foo avec ".
@_." arguments : ".join(", ", @_)."\n";$arg1 = shift;$arg2 = shift;# ou ($arg1, $arg2) = @_;return $arg1 + $arg2;
}
print foo(5, 9, 123);# Too many arguments
Formation Perl
47
Fonctions
sub foo {%param = @_;return $param{bar} + $param{baz};
}
print foo(bar => 31, baz => 42);
Formation Perl
48
Fichiers
local $/;open $fh, 'fichier.txt';$_ = <$fh>;
Formation Perl
49
Fichiers
local $/;open $fh, $f or die "Err. lecture $f : $!";$_ = <$fh>;
Formation Perl
50
Fichiers
use autodie;
open $fh1, 'fichier1';open $fh2, 'fichier2';…
Formation Perl
51
Fichiers
while (<$fh>) {print "J'ai lu : $_";
}
while (<$fh>) {chomp;print "J'ai lu : $_ et je continue...\n";
}
while ($ligne = <$fh>) {chomp $ligne;print "J'ai lu : $ligne et je continue...\n";
}
Formation Perl
52
Fichiers
open $fh, '>', $f or die "Err. écriture $f : $!";# ouopen $fh, '>>', $f or die "Err. ajout $f : $!";
print $fh "bla bla\n";
close $fh;
open $fh, $f or die "Err. lecture $f : $!";# ouopen $fh, '<', $f or die "Err. lecture $f : $!";
# perldoc f open
Formation Perl
53
Fichiers
open $fh, '<:encoding(UTF8)', 'fichier.txt';
open $fh, '>:encoding(UTF8)', 'fichier.txt';
# perldoc f open
Formation Perl
54
Processus
$phrase = "Il joue et reçoit une claque sur la joue.";
$resultat = `echo $phrase | treetaggerfrench`;
open($ph, "|", "echo $phrase | treetaggerfrench");while (<$ph>) {
print unless /\tDET:ART\t/;}
open($ph, "|", "treetaggerfrench > resultat.txt");foreach $phrase (@phrases) {
print $ph $phrase;}close $ph;
Formation Perl
55
Fichiers
use autodie;
opendir($dh, '.'); # ou '/un/dossier/quelquepart'while ($item = readdir $dh) {
if (f $item) {print "$item est un fichier (un vrai)\n";
} elsif (d $item) {print "$item est un dossier\n";
}}closedir $dh;
# perldoc f opendir# perldoc f X
Formation Perl
56
Fichiers
foreach $item (glob '*.xml') {if (f $item) {
print "$item est un fichier (un vrai)\n";} elsif (d $item) {
print "$item est un dossier\n";}
}
# (mkdir piège.xml)
Formation Perl
57
Fichiers
foreach (glob '*.xml') {if (f) {
print "$_ est un fichier (un vrai)\n";} elsif (d) {
print "$_ est un dossier\n";}
}
Formation Perl
58
Fichiers
use autodie;unlink 'fichier'; # attention !mkdir 'répertoire';rmdir 'répertoire';# récursif => use File::Path;rename 'fichier', 'fichier.old';# ou use File::Copymove('fichier', 'fichier.old');
use File::stat;$a = stat("fichier.txt");print "Taille de fichier.txt : ".$a>size." octets\n";# perldoc File::stat
Formation Perl
59
Bases de données
use DBI;use DBD::mysql;
$dbh = DBI>connect("dbi:mysql:BASE:SERVEUR", "USER", "PASSWORD");
$sth = $dbh>prepare("select * from TABLE where a=? and b=?");$sth>execute($a,$b);
print $sth>rows."\n";
while($row = $sth>fetchrow_hashref) { print $row>{"a"}."\n";}
Formation Perl
60
HTTP
use LWP::Simple;
$xml = get "http://localhost:8983/solr/select/?q=test";
# perldoc LWP::Simple# perldoc LWP
Formation Perl
61
XML<?xml version='1.0'?><library> <book>
<isbn>0596001320</isbn> <title>Apprendre Perl, 3ème édition</title> <author>Randal L. Schwartz</author> <author>Tom Phoenix</author> </book> <book> <isbn>1565922204</isbn> <title>Perl, programmation avancée</title> <author>Sriram Srinivasan</author> </book> <book> <isbn>076455106X</isbn> <title>La guitare pour les nuls</title> <author>Mark Phillips</author> <author>John Chappell</author> </book></library>
Formation Perl
62
XML
local $/;open $fh, 'fichier.xml';$_ = <$fh>;
while (s!<book>.*?</book>!!s) { $book = $&; $book=~m!<title>(.*?)</title>!; $titre = $1; next unless $titre=~/perl/i; while ($book=~s!<author>(.*?)</author>!!s) { push @auteurs, $1; } print uc($titre)." : ".join(", ", @auteurs)."\n"; undef @auteurs;}
Formation Perl
63
XML
use XML::Simple;
$library = XMLin('fichier.xml', ForceArray => ['author']);
foreach $book (@{$library>{book}}) { # pas si simple...next unless $book>{title}=~/perl/i;print uc($book>{title})." : ".
join(', ', @{$book>{author}})."\n";}
Formation Perl
64
XML
use XML::Twig;
$twig = XML::Twig>new();$twig>parsefile('fichier.xml');
foreach $book ($twig>root>children('book')){$titre = $book>first_child_text('title');next unless $titre=~/perl/i;print uc($titre)." : ".
join(', ', $book>children_text('author'))."\n";}
Formation Perl
65
XML
use XML::LibXML;
$parser = XML::LibXML>new();$doc = $parser>parse_file('fichier.xml');
foreach $book ($doc>findnodes('/library/book')) { $titre = $book>findnodes('title')>to_literal; next unless $titre=~/perl/i; @auteurs = map { $_>to_literal }
$book>findnodes('author'); print uc($titre)." : ".join(", ", @auteurs)."\n";}
Formation Perl
66
XML
# autres...
# XML::Parser : trop « bas niveau » (trop complexe)
# XML::Path : similaire à XML::LibXML (DOM, Xpath) mais # moins efficace et n'est plus maintenu.
# XML::DOM : première implémentation de DOM, mais # n'est plus maintenu.
# conclusion : XML::LibXML ou XML::Twig ou … XML::LibXSLT ?
Formation Perl
67
XML<?xml version='1.0'?><library xmlns="http://truc.org/foobar_1.0"> <book>
<isbn>0596001320</isbn> <title>Apprendre Perl, 3ème édition</title> <author>Randal L. Schwartz</author> <author>Tom Phoenix</author> </book> <book> <isbn>1565922204</isbn> <title>Perl, programmation avancée</title> <author>Sriram Srinivasan</author> </book> <book> <isbn>076455106X</isbn> <title>La guitare pour les nuls</title> <author>Mark Phillips</author> <author>John Chappell</author> </book></library>
Formation Perl
68
XML
use XML::LibXML;
$parser = XML::LibXML>new();$doc = $parser>parse_file('fichierb.xml');$xc = XML::LibXML::XPathContext>new(
$doc>documentElement());$xc>registerNs(fb => 'http://truc.org/foobar_1.0');
foreach $book ($xc>findnodes('/fb:library/fb:book')) { $titre = $xc>findnodes('fb:title', $book)>to_literal; next unless $titre=~/perl/i; @auteurs = map { $_>to_literal }
$xc>findnodes('fb:author', $book); print uc($titre)." : ".join(", ", @auteurs)."\n";}
# plutôt un « préprocessing » si pas de risque de clash ?
Formation Perl
69
XSLT
use XML::LibXSLT;use XML::LibXML;
$xslt = XML::LibXSLT>new();
$xml = XML::LibXML>load_xml(location => 'fichier.xml');$xsl = XML::LibXML>load_xml(location => 'fichier.xsl');
$stylesheet = $xslt>parse_stylesheet($xsl);$results = $stylesheet>transform($xml);print $stylesheet>output_as_bytes($results);
Formation Perl
70
XSLT<?xml version='1.0'?> <xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:t="http://truc.org/foobar_1.0" version="2.0"><xsl:output method="text" indent="no" />
<xsl:template match="/t:library"> <xsl:applytemplates select="t:book[matches(t:title, 'perl', 'i')]"/></xsl:template>
<xsl:template match="t:book"> <xsl:valueof select="uppercase(t:title)" /> <xsl:text> : </xsl:text> <xsl:applytemplates select="t:author" /></xsl:template>
<xsl:template match="t:author"> <xsl:valueof select="." /> <xsl:choose> <xsl:when test="position()=last()"> <xsl:text></xsl:text> </xsl:when> <xsl:otherwise> <xsl:text>, </xsl:text> </xsl:otherwise> </xsl:choose></xsl:template>
</xsl:stylesheet>
Formation Perl
71
XSLT 1 + XML::LibXSLT<?xml version='1.0'?><xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:foo="urn:foo" xmlns:t="http://truc.org/foobar_1.0" version="1.0"><xsl:output method="text" indent="no" />
<xsl:template match="/t:library"> <xsl:applytemplates select="foo:matches(t:book, 'perl')" /></xsl:template>
<xsl:template match="t:book"> <xsl:valueof select="foo:uc(t:title)" /> <xsl:text> : </xsl:text> <xsl:applytemplates select="t:author" /></xsl:template>
<xsl:template match="t:author"> <xsl:valueof select="." /> <xsl:choose> <xsl:when test="position()=last()"> <xsl:text></xsl:text> </xsl:when> <xsl:otherwise> <xsl:text>, </xsl:text> </xsl:otherwise> </xsl:choose></xsl:template>
</xsl:stylesheet>
Formation Perl
72
XSLT1 + XML::LibXSLTsub matches { $nodelist = shift; $pattern = shift; $matches = XML::LibXML::NodeList>new; foreach $node ($nodelist>get_nodelist) { if ($node>to_literal =~ /$pattern/i) { $matches>push($node); } } return $matches;}
XML::LibXSLT>register_function("urn:foo", "matches",\&matches);
XML::LibXSLT>register_function("urn:foo", "uc", sub { uc($_[0]) });
Formation Perl
73
Le XML est trop gros / Pas assez de RAM
use XML::Twig;
$twig = XML::Twig>new(Twig_handlers => {'ExternalPage' => \&handle_external_page});
$twig>parsefile($ARGV[0]);
sub handle_external_page { ($twig, $twig_external_page) = @_; $titre = uc($twig_external_page>field('d:Title')); next unless $titre =~/perl/i; $desc = $twig_external_page>field('d:Description'); $desc =~s/\n//gs; print "$titre : $desc\n"; $twig>purge;}
Formation Perl
74
Découper un fichier XML
open($fh, "<", $ARGV[0]);while (<$fh>) {
$morceau .= $_;if (length($morceau) > 100_000_000) {
ecrit_morceau();}
}ecrit_morceau();
sub ecrit_morceau {$n++;print "morceau n° $n\n";open($fh2, ">", "morceau$n.xml");$morceau =~ s!<ExternalPage.*</ExternalPage>!!gs;print $fh2 $&;close $fh2;
}
Formation Perl
75
Produire du XML
%livres = ( 'R. Schwartz' => 'Apprendre Perl','S. Srinivasan' => 'Programmation avancée' );
use XML::LibXML;$doc = XML::LibXML::Document>new('1.0', 'utf8');$racine = $doc>createElement('books');$doc>setDocumentElement($racine);
while (($auteur, $titre) = each %livres) {$article = $doc>createElement('book');$article>setAttribute('author', $auteur);$article>appendTextNode($titre);$racine>appendChild($article);
}
print $doc>toString(1);
Formation Perl
76
Valider du XML / schéma
use XML::LibXML;
$schema = XML::LibXML::Schema>new(location=>'schema.xsd');$parseur = XML::LibXML>new();$doc = $parseur>parse_string($xml); # ou parse_file(...)
eval {$schema>validate($doc);
};
if ($@) {print "La validation a échoué : $@\n";
} else {print "OK, valide !\n";
}
# Element 'book': The attribute 'author' is required but missing.
Formation Perl
77
Valider du XML / DTD
use XML::LibXML;
$parseur = XML::LibXML>new();$parseur>validation(1);
eval {$doc = $parseur>parse_string($xml); # ou parse_file
};
if ($@) {print "La validation a échoué : $@\n";
} else {print "OK, valide !\n";
}
# Element book does not carry attribute author
Formation Perl
78
Du prototype à la prod'
use strict;
my $foo = 'bar';
# …
print "Voici la valeur de foo : $fooo\n";
# => Global symbol "$fooo" requires explicit package name# « compilation errors »
Formation Perl
79
Du prototype à la prod'
# mais ça ne fait pas tout...use strict;
my $foo = 'bar';
# …
$foo =~s/\w//g;
print "Voici la valeur de foo : $foo\n";
Formation Perl
80
Du prototype à la prod'
# fichier MesFonctions.pm :
package MesFonctions;
use strict;
our $CONSTANTE = 123;
sub DateFormatPerso {use POSIX qw(strftime);return strftime "%Y%m%d %H:%M:%S", localtime;
}
Formation Perl
81
Du prototype à la prod'
# script utilisant le module :
use MesFonctions;
print "$MesFonctions::CONSTANTE\n";
print MesFonctions::DateFormatPerso();
Formation Perl
82
Références
Manuels et tutoriels « perldoc » en françaishttp://perl.enstimac.fr/
Réponses dignes de confiance, en anglaishttp://www.perlmonks.org/http://stackoverflow.com/
FAQ XML Perl en anglaishttp://perlxml.sourceforge.net/faq/XML et Perl en françaishttp://djibril.developpez.com/tutoriels/perl/perlxml/
Formation Perl