back to top

Guida Perl

Perl (acronimo di Practical Extraction and Report Language), è un linguaggio versatile che può essere utilizzato sia per scivere applicativi lato server (ed in particolare scripts CGI) che per creare software più avanzati compatibili con i file system dei più diffusi sistemi operativi in circolazione.

Questo linguaggio è stato ideato dallo sviluppatore Larry Wall seguendo due principi fondamentali: il primo si basa sul motto "There’s more than one way to do it", cioè "Esiste più di un modo per ottenere uno stesso risultato"; il secondo si basa sull’esigenza di mettere a disposizione degli sviluppatori un semplice strumento con cui poter produrre applicativi senza far ricorso a linguaggi troppo avanzati.

Alla luce dell’evoluzione di cui il Perl ha goduto in questi anni, possiamo dire che i due principi fondanti che hanno ispirato l’autore sono stati pienamente rispettati. Esso permette di affrontare diverse metodologie di approccio per la soluzione delle problematiche di sviluppo e, nello stesso tempo, di creare applicativi in modo più semplice e veloce di quanto non consentano altri linguaggi più ostici come C e C++.

Per essere chiari, Perl non è un "concorrente" degli ultimi due linguaggi citati, ma una risorsa a cui ricorrere quando vogliamo creare applicativi per cui sarebbe "frustrante" affrontare lunghe sessioni di lavoro in C e C++. Quindi, per citare Larry Wall, se siete "pigri" e "impazienti", Perl è il linguaggio che fà per voi.

Procurarsi Perl non è difficile, lo troverete disponibile gratuitamente nella sezione download di Perl.org; al momento, l’ultima versione stabile è la 5.8.7 e può essere utilizzata sia nel sua ambiente naturale, UNIX, che in altri sistemi diffusi con Linux, MAC e Windows.

L’installazione e la configurazione di Perl non presentano alcuna difficoltà: se utilizzate Linux, nella stragrande maggioranza dei casi esso sarà già installato e pronto da utilizzare; se utilizzate Windows, potrete procurarvi l’apposito pacchetto auto-installante all’indirizzo indicato e seguire la procedura guidata.

Perl è un linguaggio Open Source, questo significa che il suo codice sorgente è "aperto" a chiunque, dotato di capacità e di buona volontà, voglia partecipare volontariamente al suo sviluppo.

Nelle pagine che seguiranno descriveremo le basi di questo linguaggio cercando di introdurre logiche, meccanismi e costrutti che stanno alla base del Perl.

Il nostro primo script in Perl

La sintassi del Perl è estremamente semplice, il lettore non avrà quindi particolari difficoltà nel comprendere la funzione del breve esempio di scripting che proponiamo nelle righe seguenti:

#!/usr/local/bin/perl 
# 
# Il nostro primo script in Perl 
# 
print 'Funziona!';

Analizziamo il nostro piccolo applicativo nelle sue singole parti. Innanzitutto, abbiamo una parte introduttiva che è presente in tutti gli script creati con Perl:

#!/usr/local/bin/perl

La sintassi in certi casi può variare a seconda delle impostazioni del file system presenti nella macchina utilizzata, in Windows potrebbe essere per esempio "#!C:\perl\bin\perl.exe", ma la logica di base è sempre la stessa. Questa stringa, riferita al precorso in cui si trova l’esecutore del Perl, comunica un’istruzione al sistema operativo indicandogli quale operazione svolgere nel momento in cui il file contenente il codice deve essere eseguito; nello specifico, la riga introduttiva eprime un comando che invia il file ".pl" (chiamiamolo come vogliamo, "funziona.pl" và benissimo, conta l’estensione) all’esecutore Perl.

In secondo luogo, introduciamo i commenti, un’opportunità importante e troppo spesso trascurata per tenere continuamente traccia dei vari passaggi utilizzati in sede di digitazione del codice; i commenti non vengono eseguiti nè vengono visualizzati, sono semplicemente dei pro-memoria utili per ricordare dove e perché abbiamo inserito determinati frammenti di listato.

I commenti, vengono introdotti tra le righe di uno script attraverso il simbolo del cancelletto (#), quest’ultimo deve precedere i commenti, tutto ciò che si trova compreso tra il cancelletto e la fine della riga non dovrà essere eseguito nè stampato a video. La riga introduttiva in cui viene passato il file all’esecutore Perl, costituisce naturalmente un’eccezione in quanto, nonostante sia preceduta dal cancelletto, viene comunque eseguita. Se si desidera scrivere di seguito più righe di commenti, sarà necessario inserire all’inizio di ogni riga un cancelletto come nell’esempio che proponiamo di seguito:

#!/usr/local/bin/perl 
# 
# commento
# commento
# commento
# 
istruzione;

E’ molto importante non dimenticarsi di porre il simbolo del cancelletto all’inizio di ogni commento, diversamente l’esecutore del Perl potrebbe interpretare quanto scritto come parte integrante del codice e restituire un errore.

Passiamo ora alla parte finale del nostro piccolo script, si tratta di un’istruzione che determina in output la visualizzazione di una breve stringa di testo:

print 'Funziona!';

print è un costrutto nativo del Perl che viene utilizzato per la stampa a video degli output, nel nostro caso gli è stata passata come parametro la stringa "Funziona!" la cui visualizzazione è lo scopo finale dello script.

Sono ora da sottolineare due particolarità che riguardano la sintassi Perl in generale. Innanzitutto la stringa è stata delimitata da apici (‘Funziona!’), questo è un elemento fondamentale in quanto in mancanza degli apici l’esecutore Perl non sarebbe in grado di riconoscerla come tale. In secondo luogo, l’istruzione è stata conclusa con un punto e virgola, si tratta anche in questo caso di un elemento necessario, in quanto il punto e virgola "chiude" un’istruzione rendendola eseguibile.

Eseguire uno script in Perl

Coloro che hanno anche soltanto un pò pratica nell’utilizzo del linguaggio di scripting server side PHP, osservando il codice del breve script proposto nella lezione precedente, avranno certamente notato le numerose affinità esistenti tra la sintassi di questo linguaggio e quella utilizzabile per digitare listati scritti in Perl.

Potremmo quindi "tradurre" lo script dal Perl in PHP introducendo alcune lievi modifiche fra le righe:

<?
#Stampare a video una stringa con PHP
print 'Funziona!';
?>

Come si potrà notare, in PHP rispetto al Perl abbiamo lo stesso modo di inserire commenti (tramite il cancelletto), la stessa funzione per la visualizzazione delle stringhe (print), la stessa procedura per delimitare le stringhe (utilizzare gli apici) e infine, lo stesso segno per chiudere le istruzioni (il punto e virgola).

Le similitudini non si fermano qui, infatti, che sia vero o no il Perl è da molti ritenuto come una specie di "PHP semplificato". Vi sono comunque delle differenze importanti che vanno in ogni caso sottolineate.

Gli script in Perl, per esempio, vengono eseguiti tramite procedure differenti rispetto a quelle utilizzate per PHP. Un volta digitato il codice con il nostro editor di testo preferito (non importa quale, ma le alternative "semplici" come il Vim di Linux sono sempre le migliori per digitare codice "pulito"), dovremo salvare lo script in un file ".pl". Ora, dovremo rendere l’applicativo eseguibile, per far questo sarà necessario impostare i relativi permessi sul programma utilizzando l’apposita istruzione da Shell:

chmod u+x nome_programma

Nell’ istruzione proposta, abbiamo innanzitutto il comando chmod (abbreviazione di change mode) che serve per settare i permessi sui file; vi sono poi gli argomenti (opzioni) u (user) e x (execute); infine, abbiamo il parametro da passare al comando nell’istruzione, cioè il nome del nostro programma.

Una volta impostati i permessi di esecuzione potremo eseguire il nostro script tramite l’istruzione:

./nome_programa

come alternativa possiamo digitare anche:

perl nome_programa

oppure, più semplicemnte:

nome_programa

A questo punto lo script verrà eseguito, se il codice è stato salvato correttamente verrà stampata a video la stringa attesa; nel momento in cui entrerà in azione l’esecutore Perl, il sorgente verrà in primo luogo compilato e sarà l’output del processo di compilazione ad essere eseguito. I tempi di attesa variano a seconda della complessità dell’applicativo, ma nel nostro caso saranno naturalmente minimi.

Nel caso in cui il nostro codice sia stato scritto in modo corretto, dovremmo ricevere una notifica di errore, ma è altrettanto probabile che il sistema non ci comunichi nulla e si limiti a non eseguire il programma. Vi è comunque la possibilità di richiedere al sistema dei messaggi riguardanti lo stato e gli esiti dell’esecuzione:

perl -w nome_programma

Sarà inoltre possibile eseguire lo script in debugging tramite la seguente istruzione:

perl -d nome_programma

Le variabili

Una variabile, è descrivibile come un "contenitore di informazioni", si tratta infatti di un elemento del linguaggio che attraverso una precisa sintassi svolge la funzione di rappresentare un determinato valore assegnato ad esso.

Le variabili possono rappresentare diversi tipi di valori, è possibile infatti stabilire per esse sia valori numerici (interi, decimali, negativi, positivi..), sia sequenze di caratteri alfabetici, numerici o simbolici dette stringhe.

Per "dichiarare" una variabile, cioè per renderla "esistente", è necessario dare ad essa un nome preceduto dal simbolo del dollaro ("$") e assegnare a questo nome un valore tramite il segno "=" (uguale) chiamato "operatore di assegnazione".

Il nome da utilizzare per dichiarare una variabile può essere costituito sia da numeri che da lettere dell’alfabeto, è inoltre possibile utilizzare l’underscore (ad esempio: "$var_1"). Non è possibile che il nome di una variabile cominci con un numero, nè porre l’underscore subito dopo il dollaro ("$_" è un costrutto particolare da utilizzare in altri casi).

Perl è un linguaggio case sensitive, quindi è in grado di distinguere tra lettere minuscole e maiuscole, ne consegue che "$var" e "$Var" verranno considerate come due variabili ben distinte.

Il processo di assegnazione di un valore stringa ad una variabile avviene in questo modo:

$var = 'stringa';

Invece, l’assegnazione di un valore numerico ad una variabile dovrà avvenire in quest’altro modo:

$var = 56

Quindi utilizzeremo gli apici per indicare che il valore che stiamo assegnando è un stringa, mentre gli ometteremo per assegnare un valore numerico. Ne consegue che anche un numero potrà essere assegnato come valore stringa ad una variabile semplicemente utilizzando gli apici:

$var = '109';

Gli Array

Fondamentalmente gli array sono anch’essi delle variabili, ma di un tipo particolare, infatti, con questo termine usiamo identificare una variabile che racchiude in sè (a cui sono stati assegnati) più valori.

Per dichiarare un array si utilizza una sintassi molto simile a quella che viene impiegata per le variabili, in questo caso, però, dovremo sostituire il dollaro con una chiocciola ("@") ed elencare i valori da assegnare all’array ponendoli tra parentesi tonde e suddividendoli tramite una virgola. Quindi, nel caso in cui volessimo dichiarare una variabile array chiamata, per esempio, "@array", dovremo utilizzare una sintassi simile alla seguente:

@array = ("valore_1", "valore_2", "valore_n");

Un array chiamato "@famiglia" potrebbe per esempio essere strutturato in questo modo:

@array = ("padre", "madre", "figlio", "figlia");

Dato che un array non rappresenta un unico valore, ma è comunque rappresentato da un unico nome, si pone il problema di estrarre i singoli valori da esso. Per far questo Perl assegna ai valori che compongono un array un indice numerico che và da "0" a "n", dove "0" rappresenta il numero indice del primo valore ed "n" quello dell’ennesimo valore contenuto. Per cui nel nostro array "@famiglia" avremo che "padre" è rapresentato dal numero indice "0", mentre "figlia" è rappresentato dall’ultimo numero indice, cioè "3". Se volessimo estrarre il valore "madre" dall’array "@famiglia", dovremmo indicare tra parentesi quadre il numero indice corrispondente al valore prescelto (in questo caso "1" in un indice numerico che và da "0" a "3"). Quindi, in pratica avremo:

$famiglia[1]

Che è pari a "madre", da notare che in questo caso utilizzeremo "$" e non "@" in quanto "$famiglia[1]" rappresenta un unico valore ed è quindi una normale variabile non composita. Una volta dichiarato un array, in un secondo tempo è possibile allocare all’interno di esso ulteriori valori tramite l’istruzione "push" (letteralmente "spingi"). Quindi, se per esempio volessimo accodare il valore "nonno" a quelli già presenti nel nostro array "@famiglia" potremmo utilizzare la seguente istruzione:

push(@famiglia, "nonno");

In questo caso "nonno" assumerà un numero indice pari a "4" (quinto per un indice che và da "0" a "4"). Se desiderassimo aggiungere più di un ulteriore valore all’array dovremmo "annidare" le parentesi tonde:

push(@famiglia, ("nonno", "nonna"));

Sarà inoltre possibile che un array presenti un array (o più di uno) tra i suoi valori:

@array = ("padre", "madre", "figlio", "@nonni");

Un array può essere assegnato ad una comune variabile, ma in questo caso dovremo porre particolare attenzione all’uso degli apici, infatti:

$var = @famiglia;

consite nell’assegnazione alla variabile "$var" della lunghezza dell’array denominato "@famiglia", mentre:

$var = '@famiglia';

opera una sotituzione tramite una stringa del nome di un array, la stringa rappresenterà i valori separati da spazi.

I comuni array consentono l’accesso al loro contenuto tramite l’indice numerico, ma è inoltre possibile creare array con elementi accessibili tramite stringhe; in questo caso parliamo di array associativi:

%dati = (
  "giuseppe garibaldi", 50,
  "john lennon", 99,
  "linus torvald", 44
);

Per cui, per esempio:

$dati{"linus torvald"};

restituirà "44".

Operare con le variabili

Una volta valorizzate le nostre variabili, potremo utilizzare le informazioni in esse contenute per svolgere numerosi tipi di operazioni con e su di esse, ciò sarà reso possibile dall’impiego di particolari costrutti nativi messi a disposizione dal Perl, chiamati appunto "operatori".

I primi operatori che analizzeremo saranno quelli di tipo matematico che ci consentono di effettuare semplici operazioni aritmetiche come le addizioni, le sottrazioni, le divisioni, le moltiplicazioni, il calcolo delle potenze, incrementi e decrementi etc.. Si tratta di operatori comuni ad altri linguaggi utilizzabili per lo scripting server side e non solo.

L’operatore di addizione è rappresentato dal segno "+", esso ci consente di sommare i valori contenuti in due o più variabili di tipo numerico oppure, come nell’esempio che segue, di allocare all’interno di una variabile il risultato della sommatoria tra due valori numerici:

$var = 4 + 5;

L’operatore di sottrazione è rappresentato dal segno "", esso ci permette di calcolare la differenza tra i valori contenuti in due variabili o più di tipo numerico oppure, come nell’esempio seguente, di salvare all’interno di una variabile il risultato della differenza fra valori numerici:

$var = 5 - 4;

L’operatore di moltiplicazione viene rappresentato tramite il segno "*", esso ha la funzione di calcolare il prodotto ottenuto dalla moltiplicazione di valori contenuti in due o più variabili di tipo numerico oppure, di salvare all’interno di una variabile il risultato della moltiplicazione fra valori numerici:

$var = 4 * 5;

L’operatore di divisione simboleggiato dallo slash, "/", ha il compito di calcolare il risultato ottenuto dalla divisione di valori contenuti in variabili numeriche oppure, di salvare all’interno di una variabile il risultato della divisione fra valori numerici:

$var = 4 * 5;

Per calcolare la potenza di un numero, utilizzaremo il simbolo "**", preceduto dalla cifra che vogliamo elevare e succeduto dall’esponente, ad esempio, per elevare "4" alla quinta scriveremo:

$var = 4 ** 5;

Per calcolare il resto di una divisione utilizzaremo il simbolo percentuale, "% "(modulo), ad esempio, per ottenere il resto della divisione "5/4" scriveremo:

$var= 5 % 4;

Per il calcolo d’incremento e decremento utilizzaremo rispettivamente gli operatori "++" (incrementa di "1") e "–" (decrementa di "1"), quindi, data "$var=n" avremo che:

# Incremento unitario della variabile
++$var; 
# Incremento unitario di $var + 1 
$var++; 
# Decremento unitario della variabile
--$var; 
# Decremento unitario di $var - 1 
$var--;

Nel corso di questa guida abbiamo già analizzato l’operatore di assegnazione "=", esso può essere utilizzato anche per attribuire ad una variabile il valore di un’altra variabile:

$var = $var_1;

Può inoltre essere utilizzato per incrementare il valore di una variabile in associazione all’operatore "+".

#associazione di un incremento unitario ad una nuova variabile
$var += $var_1;

Oppure può essere impiegato per decrementare il valore di una variabile in associazione all’operatore "".

#associazione di un decremento unitario ad una nuova variabile
$var -= $var_1;

Per quanto riguarda le stringhe, oltre ad "=" valido anche per esse, introduciamo l’operatore di concatenazione "." che potrà essere utilizzato come segue:

$var = $var_1.$var_2

oppure

$var. = $var_1

Nel primo caso creiamo una nuova variabile il cui valore è uguale alla concatenazione di due altre variabili (ad esempio, date "$var_1=’ciao’" e "$var_2=’Max’", avremo che "$var" è uguale a "’Ciao Max’"). Nel secondo caso, una variabile già nota assume un nuovo valore concatenando il proprio a quello di un’ulteriore variabile.

Un esempio di concatenazione tra stringhe all’interno di un’istruzione è il seguente:

print $var.' e '.$var_1;

Per passare due parametri come una sola stringa utilizzeremo invece:

print "$var and $var_1";

i doppi apici ci consentiranno in fatti di rimpiazzare i nomi delle variabili con i loro rispettivi valori.

Operatori per il controllo del flusso

Perl vede le istruzioni come se fossero delle funzioni per cui restituisce un valore in output, quest’ultimo può essere interpretato in senso booleano come TRUE o come FALSE. Il valore "1" oppure una stringa non vuota e diversa da "0" sono TRUE, al contrario, il valore "0" o una stringa vuota sono FALSE.

Gli operatori booleani o logici ragionano in senso binario, cioè una dichiarazione può essere vera o falsa e sono impiegati in genere per le istruzioni condizionali come if, else ed elsif (omologa dell’elseif in altri linguaggi), oppure, per i cicli come for e while.

Tra gli operatori booleani citiamo:

  • AND: ad esempio: $var && $var_1; l’espressione logica sarà vera se "$var" e "$var_1" sono entrambe TRUE altrimenti sarà falsa.
  • OR: ad esempio: $var || $var_1; l’espressione logica sarà vera se almeno una delle due variabili lo è altrimenti sarà falsa.
  • NOT: ad esempio: !$var; l’espressione sarà vera se "$var" non lo è altrimenti sarà falsa.

Gli operatori di confronto, invece, generano un output sulla base di un confronto tra variabili; in questo caso è molto importante poter confrontare tipologie di dato omogenee, quindi Perl dedica nativamente operatori specifici con i quali potremo operare confronti tra variabili numeriche, tra stringhe e tra file.

Tra gli operatori per i confronti numerici citiamo:

  • L’operatore di uguaglianza. Ad esempio: $var == $var_1; restituisce TRUE se le variabili sono identiche tra loro per valore.
  • L’operatore di minoranza. Ad esempio: $var < $var_1; restituisce TRUE se la prima variabile ha un valore inferiore rispetto a quello della seconda.
  • L’operatore di minoranza o uguaglianza. Ad esempio: $var <= $var_1; restituisce TRUE se la prima variabile ha un valore inferiore o uguale a quello della seconda.
  • L’operatore di maggioranza. Ad esempio: $var > $var_1; restituisce TRUE se la prima variabile ha un valore maggiore rispetto a quello della seconda.
  • L’operatore di maggioranza o uguaglianza. Ad esempio: $var >= $var_1; restituisce TRUE se la prima variabile ha un valore maggiore o uguale a quello della seconda.
  • L’operatore di diversità o di negazione. Ad esempio: $var != $var_1; restituisce TRUE se le variabili sono diverse tra loro per valore.

Tra gli operatori per i confronti tra le stringhe citiamo:

  • L’operatore di uguaglianza. Ad esempio: $var eq $var_1; restituisce TRUE se le variabili sono identiche tra loro.
  • L’operatore di minoranza. Ad esempio: $var lt $var_1; restituisce TRUE se la prima variabile ha un valore inferiore per ordine alfabetico rispetto a quello della seconda.
  • L’operatore di minoranza o uguaglianza. Ad esempio: $var le $var_1; restituisce TRUE se la prima variabile ha un valore inferiore o uguale per ordine alfabetico a quello della seconda.
  • L’operatore di maggioranza. Ad esempio: $var gt $var_1; restituisce TRUE se la prima variabile ha un valore maggiore per ordine alfabetico rispetto a quello della seconda.
  • L’operatore di maggioranza o uguaglianza. Ad esempio: $var ge $var_1; restituisce TRUE se la prima variabile ha un valore maggiore o uguale per ordine alfabetico a quello della seconda.
  • L’operatore di diversità o di negazione. Ad esempio: $var ne $var_1; restituisce TRUE se le variabili sono diverse tra loro.

Infine, citiamo alcuni tra gli operatori per il confronto tra file:

  • -r, ad esempio: -r $var; restituisce TRUE se il file associato alla variabile è leggibile.
  • -w, ad esempio: -w $var; restituisce TRUE se il file associato alla variabile è scrivibile.
  • -d, ad esempio: -d $var; restituisce TRUE se alla variabile è associata una directory.
  • -f, ad esempio: -f $var; restituisce TRUE se alla variabile è associato un file regolare.
  • -T, ad esempio: -T $var; restituisce TRUE se alla variabile è associato un file di testo .
  • -e, ad esempio: -e $var; restituisce TRUE se alla variabile è associato un file esistente.

Istruzioni condizionali

Quando si parla di istruzioni condizionali o di costrutti per il controllo del flusso, chi conosce un minimo di sintassi dello scripting in qualsiasi linguaggio pensa immediatamente ad if ed else. Essi consentono di intervenire sul flusso delle istruzioni di un applicativo a seconda che una determinata condizione sia verificata o meno.

La sintassi da utilizzare per effettuare controlli su condizione tramite if ed else è la seguente:

if (condizione) { 
istruzioni da eseguire se si verifica la condizione
} else { 
istruzioni da eseguire se non si verifica la condizione
}

Se (if) la condizione delimitata dalle parentesi tonde viene verificata (è TRUE), allora verrà eseguito il blocco d’istruzioni successivo all’if e racchiuso fra le parentesi graffe; altrimenti (else) verrà eseguito il blocco di istruzioni successivo ad else. Una volta passati i controlli stabiliti nei due blocchi, il flusso dei dati riprenderà con le istruzioni successive alla chiusura dell’ultima parentesi graffa.

else è un costrutto opzionale, possiamo inserirlo o meno a seconda che si voglia o no stabilire un’istruzione alternativa a quella indicata per la condizione. In mancanza di un’alternativa, se viene soddisfatta la clausola stabilita nella condizione verrà eseguito il blocco di istruzioni delimitato dalle parentesi graffe successive alla condizione, quindi, l’esecuzione dell’applicativo proseguirà seguendo le istruzioni succesive alla parentesi graffa chiusa. In caso contrario, se la condizione è FALSE, allora le istruzioni racchiuse tra le parentesi graffe non verranno eseguite ed il flusso continuerà ignorando quanto stabilito per la condizione.

L’istruzione condizionale if può essere espressa anche in modi differenti con grandi vantaggi in termini di quantità di codice da digitare; un caso particolare è quello riferito alla sintassi con notazione post-fissa, per cui gli elementi del costrutto potranno presentarsi nel modo seguente:

istruzione if condizione;

In questo caso non verranno utilizzate parentesi, nè tonde nè graffe, quindi, la singola istruzione verrà eseguita soltanto nel caso in cui si verifichi la condizione stabilita.

Volendo proporre un esempip di applicazione pratica delle istruzioni di controllo, è importante dire che esse possono essere utilizzate anche in associazione ad operatori per affinare la condizione stabilita:

if (!$var) 
# ! richiede l'inesistenza di $var 
{ print "Prima condizione verificata\n"; } 
# invece se  
elsif ($var == $var_1) 
{ print "Seconda condizione verificata\n"; } 
# invece se  
elsif ($var == $var_2) 
{ print "Terza condizione verificata\n"; } 
# se non si verificano le condizioni:
else { print "Nessuna condizione verificata\n"; }

Nello script appena proposto abbiamo alcune importanti novità da segnalare: la condizione è stabilità dall’operatore di negazione "!"; l’istruzione subalterna alla prima condizione comprente una newline ("\n") che consente di stabilire una nuova linea una volta stampato a video il risultato. Abbiamo poi due condizioni introdotte dal costrutto elsif che saranno vere soltanto se la prima condizione sarà verificata. Infine, else propone un’istruzione alternativa che produrrà il suo output soltanto dopo che (e se) i precedenti controlli avranno restituito FALSE.

I Cicli

I cicli, detti anche istruzioni di iterazione, sono dei costrutti nativi che ci consentono di eseguire ciclicamente e quindi di ripetere determinati comportamenti; per ciclo, intendiamo quindi la ripetizione di certi comandi per un determinato numero di volte.

Il ciclo for è sicuramente una delle istruzioni di iterazione maggiormente impiegata, anche perché non si tratta di un costrutto proprio soltanto del linguaggio Perl. Presentiamo di seguito un breve esempio della funzione svolta da for:

#!/usr/local/bin/perl

@famiglia = ("padre", "madre", "figlio", "figlia");

for ($i=0; $i<=$#famiglia; $i++)
{
  print "$famiglia[$i]\n";
}

Nell’esempio proposto, abbiamo utilizzato un ciclo for con lo scopo di stampare a video tutti gli elementi di un array.

Un ciclo for si ottiene utilizzando una sintassi che comprende il costrutto for seguito da tre istruzioni che hanno il compito di definire il ciclo; abbiamo poi le istruzioni che dovranno essere eseguite ripetutamente. Analizziamo le tre istruzioni per la definizione del ciclo:

  1. la prima, nel nostro caso "$i=0", stabilisce un valore iniziale; essa deve essere eseguita una sola volta ad inizio ciclo.
  2. La seconda, nel nostro caso "$i<=$#famiglia" ("$#famiglia" indica l'ultimo valore dell'array), è chiamata condizione di terminazione; essa deve essere valutata prima di ogni iterazione e restituisce FALSE quando il ciclo si interrompe.
  3. La terza, nel nostro caso "$i++", svolge la funzione di incrementare il valore dato alla prima; essa viene rieseguita ad ogni iterazione fino a quando la condizione di terminazione non restituisce FALSE e il cilclo si ferma.

Nel nostro esempio, la variabile "$i" (contatore), assume all’inizio un valore pari a "0"; ad ogni ciclo il contatore subisce un incremento unitario ("$i++"); quando il contatore raggiunge un valore pari al numero degli elementi dell’array ("$i<=$#famiglia") il ciclo termina.

Un’altro costrutto d’iterazione da analizzare è foreach, per molti versi simile a for; attraverso foreach è possibile inserire di seguito all’interno di una variabile tutti gli elementi di un array. Proponiamo quindi un esempio sull’utilizzo di questo nuovo costrutto:

#!/usr/local/bin/perl

@famiglia = ("padre", "madre", "figlio", "figlia");

foreach $famigliare (@famiglia)
{
  print "$famigliare\n";
}

Come si avrà avuto modo di notare, le differenze anche sintattiche tra foreach e for sono veramente minime. Nell’esempio proposto, ad ogni ripetizione del ciclo la variabile "$famigliare" assume un valore pari a quello dell’elemento estratto in quel momento dall’array "@famiglia".

Il costrutto di iterazione while, considerato come un particolare tipo di if ripetuta, consente di ciclare un determinato blocco di istruzioni fino a quando una condizione risulta vera, nel momento in cui essa dovesse restituire FALSE il ciclo si bloccherebbe; se la condizione dovesse risultare falsa prima di iniziare il ciclo questo non potrà essere eseguito. Vediamo un esempio:

#!/usr/local/bin/perl

@famiglia = ("padre", "madre", "figlio", "figlia");

while (@famiglia)
{
  $famigliare = shift @famiglia;
  print "$famigliare\n";
}

Grazie a while verrà visualizzato tutto il contenuto in valori dell’array famiglia.

Creare funzioni personalizzate

Le funzioni sono dei costrutti sintattici utili per produrre specifici comportamenti. Esistono principalmente due tipologie di funzioni: quelle native messe a disposizione dal linguaggio stesso, quelle personalizzate che vengono definite dallo sviluppatore in sede di scrittura del codice.

Le funzioni native messe a disposizione da Perl sono numerosissime e producono i comportamenti più disparati: vi sono funzioni per effettuare operazioni aritmetiche, per convertire tipi di dato, per manipolare stringhe, file, directory ed array etc. Non sarebbe possibile proporle tutte in questa sede, quindi consigliamo di consultare il manuale ufficiale di Perl e di sfruttare questa documentazione gratuità ogni volta che avremo bisogno di ricercare una determinata funzione per produrre un certo comportamento.

In questo capitolo, affronteremo invece il discorso riguardante le funzioni personalizzate, la cui sintassi per il Perl dovrà essere improntata sul modello della seguente:

sub funzione_personalizzata
{
  print "Istruzione 1\n";
  print "Istruzione 2\n";
}

Una funzione agisce sulla base di parametri (argomenti passati alla funzione), quando viene "richiamata". Per effettuare una chiamata dovremo porre una "&" davanti al nome effettivo della funzione:

# Chiamata semplice
&funzione_personalizzata; 

# Chiamata con un solo parametro
&funzione_personalizzata ($_); 

# Chiamata con più parametri
&funzione_personalizzata ($_1, $_2, ...);

Nel momento in cui una funzione viene richiamata, ciascun parametro viene passato come fosse una array all’interno della variabile speciale @_ che non ha alcuna relazione con la variabile $_ che è una variabile di default utilizzata per le operazioni di input e di pattern matching (ricerche all’interno di stringhe). Potremmo per esempio visualizzare i parametri passati ad una funzione attraverso una sintassi simile alla seguente:

sub view_array
{
  print "@_\n";
}

&view_array("valore_1", "valore_2", "valore_n"); 

&view_array("valore_3", "valore_4", "valore_n2");

Il discorso sulle funzioni ci porta ad affrontare quello strettamente correlato dei valori di ritorno che in una funzione sono sempre l’ultimo elemento sottoposto a valutazione. Vediamo un esempio:

sub min
{
  if ($_[0] < $_[n])
  {
    $_[0];
  }
  else
  {
    $_[n];
  }
}
$min = &min(7, 3);

Nello specifico, la funzione appena proposta restituisce il minore dei due parametri valutati.

Gestione dei file

Uno dei motivi per cui Perl è un liguaggio molto apprezzato dagli sviluppatori, risiede nella sua innata capacità di gestire le varie operazioni di manipolazione che è possibile operare su un documento, come per esempio: apertura, lettura, scrittura e chiusura.

Nelle prossime righe proporremo il codice da digitare per la creazione di un piccolo aplicativo capace di aprire, leggere e chiudere un file chiamato "documento.txt":

# Passiamo il file come valore di una variabile
$var = 'documento.txt';

# Apertura
open(INFO, $var);

# Lettura
@testo = <INFO><INFO>;

# Chiusura
close(INFO);

# stampa a video
print @testo;

La logica seguita dal nostro piccolo applicativo è abbastanza semplice: innanzitutto il file su cui operare viene passato come valore ad una variabile ("$var"); in secondo luogo utilizziamo la funzione nativa open per aprire il file; quindi, il file viene letto passando il cuo contenuto come valore di un array ("@testo"); infine il fine viene chiuso utilizzando la funzione nativa close e il suo contenuto viene stampato a video.

Sempre riguardo alla gestione dei documenti, è importante sottolineare come la funzione nativa open possa essere utilizzata anche al fine di specificare un determinato file da impiegare per il salvataggio dei dati in output:

# Lettura
open(INFO, $var);

# Scrittura
open(INFO, ">$var");

# Salvataggio
open(INFO, ">>$var");

Sarà inoltre possibile scrivere del testo su di un documento aperto in scrittura, in questo caso dovremo utilizzare l’istruzione print a cui passeremo come parametro il contenuto attuale del file (che può essere anche vuoto) e la stringa da aggiungere:

print INFO "testo testo testo testo.\n";

Pattern matching e Pattern substitution

L’ambito di utilizzo principale del linguaggio Perl, da molti ritenuto il suo campo d’applicazione "naturale", è quello relativo alla manipolazione delle stringhe attraverso operazioni di Pattern matching e di Pattern substitution.

Il Pattern matching consiste nella ricerca effettuata secondo determinati criteri di una deteminata sotto-stringa all’interno di una sequenza di caratteri; il Pattern substitution consiste invece nella sostituzione tramite un sotto-stringa di una sotto-stringa individuata all’interno di una sequenza di caratteri principale. Semplificando all’estremo, se ricerchiamo all’interno della frase "Perl è Open Source" la parola "Perl", stiamo operando un’azione di Pattern matching; se sostituiamo la parola "Perl" con la stringa "PHP", stiamo operando un’azione di Pattern substitution (mi perdonino i puristi..).

I criteri tramite i quali operare ricerche e sostituzioni vengono stabiliti tramite dei costrutti detti espressioni regolari, queste ultime "codificano" caratteri e classi di caratteri in modo da mettere a disposizione dello sviluppatore uno strumento "universalmente valido" per operare su qualsiasi tipo di stringa.

Il matching in Perl segue questa sintassi:

m/pattern/opzioni;

Proponiamo di seguito alcune possibili opzioni:

  • g: opera il matching su tutti i possibili pattern;
  • i: ignora determinati casi;
  • m: testa una stringa come multi-linea;
  • o: esprime un’unica valutazione;
  • s: vede una stringa come singola linea;
  • x: ignora gli spazi vuoti.

Le sostituzioni avvengo invece secondo la seguente sintassi:

s/pattern/sostituzione/opzioni;

Ad esempio:

s/hjhjhj/jkjkjk/;

Sostituisce la stringa "hjhjhj" con "jkjkjk".

Opzioni per le sostituzioni:

  • g: sostituzione d tutte le occorrenze;
  • i: ignora determinati casi;
  • e: valuta la stinga di sostituzione come un’espressione;
  • m: testa una stringa come multi-linea;
  • o: esprime un’unica valutazione;
  • s: vede una stringa come singola linea;
  • x: ignora gli spazi vuoti.
Pubblicitร 
Claudio Garau
Claudio Garau
Web developer, programmatore, Database Administrator, Linux Admin, docente e copywriter specializzato in contenuti sulle tecnologie orientate a Web, mobile, Cybersecurity e Digital Marketing per sviluppatori, PA e imprese.

Leggi anche...

Radice quadrata in C: vediamo come calcolarla in diversi modi

La radice quadrata è un'operazione matematica piuttosto comune (in...

Sperimentare la sequenza di Collatz in C++

Vediamo come verificare la congettura di Collatz con C++....

Calcolare la radice quadrata con Python

In Python è possibile calcolare la radice quadrata usando...

12 film che ogni programmatore dovrebbe guardare (per trovare ispirazione e creatività)

Molti ragazzi hanno deciso di intraprendere una carriera da...

Cartonizzare una foto con Python e la libreria OpenCV

La cartoonization è una procedura grafica che consente di...

Creare flowchart (diagrammi di flusso) online: 5 strumenti gratuiti

Hai bisogno di realizzare una flow chart ma non...
Pubblicitร