Fondamenti di logica booleana ed utilizzo di procedure e funzioni con esempi pratici
Open Eye realizzazione siti web- info@open-eye.it

Visual basic script: Operatori logici, funzioni e routine


Arrivati a questo punto del corso, dovremmo avere un’idea più chiara di quelle che sono le strutture logiche principali dei linguaggi di programmazione (condizioni e cicli), nonché delle definizioni di tipi di dati, variabili e costanti; abbiamo anche visto come può essere strutturato un programma un po’ più complesso che includa tutti (o quasi) questi argomenti.
In questa lezione guarderemo cosa sono e come funzionano gli operatori logici, ed affronteremo i concetti di funzione e le procedure, analizzandone i vantaggi e studiandone le reciproche differenze.

Operatori logici: TestAnd.vbs

Abbiamo visto negli esempi precedenti che qualsiasi sia la valutazione che chiediamo di fare al nostro programma (“se l’utente digita la parola “cane” allora rispondi gatto” oppure “fino a che la parola d’ordine non è pippo continua a chiedere all’utente di digitare qualcosa”) alla fine si può ricondurre tutto ad una valutazione se una determinata affermazione è vera o falsa (“la parola digitata è uguale a cane?” oppure “la parola digitata è uguale a pippo?”).
Ma cosa succede se vogliamo valutare due o più situazioni? Come facciamo a tradurre una valutazione tipo “dai il messaggio di conferma se sia la prima parola d’ordine è corretta” oppure “esci dal programma se la parola inserita dall’utente è “cane” oppure “gatto””? Bisogna adoperare gli operatori logici, ovvero and e or.

Non è nello scopo di questa lezione fare un corso di logica booleana; ci limiteremo a ricordare che nel caso di due affermazione legate dall’operatore logico “and” la valutazione finale dell’espressione è “vera” se e solo se entrambe le espressioni sono vere, ovvero:
Una tabella con gli operatori logigi booleani per l'and
Vediamo un esempio pratico che forse ci chiarisce meglio le idee… creiamo un nuovo programma TestAnd.vbs

'-------------------------------
' Name: TestAnd.vbs
' Author: Jeff Skyrunner
' Date: 22/06/10
' Desc: Risponde "Vero" se entrambi i valori inseriti
' dall'utente sono strettamente maggiori di 5
'------------------------------

' Primo valore
iPrimoValore = InputBox("Scrivi il primo numero")

' Secondo valore
iSecondoValore = InputBox("Scrivi il secondo numero")


if (iPrimoValore > 5) and (iSecondoValore > 5) Then
msgbox "Entrambi strettamente maggiori di 5"
else
msgbox "Almeno uno dei due non e' maggiore di 5"
end if

Nelle prime due istruzioni leggiamo i valori inseriti dall’utente (per questo esempio non ci interessa che il codice sia “robusto”, come si dice in gergo, ovvero non ci interessa fare i controlli che l’utente abbia effettivamente inserito un numero e non una stringa); consideriamo invece la if.

if (iPrimoValore > 5) and (iSecondoValore > 5) Then
msgbox "Entrambi strettamente maggiori di 5"
else
msgbox "Almeno uno dei due non e' maggiore di 5"
end if

l’uso dell’operatore logico And funziona proprio come nella tabella sopra riportata: la valutazione delle due espressioni (ovvero ciò che viene valutato dalla if) è vera solo se entrambe le espressioni sono vere, ovvero entrambi i numeri inseriti sono maggiori di 5. L’uso delle parentesi è fondamentale: isolare ogni singolo operatore dell’espressione logica ci permette di rendere più leggibile il codice e di essere sicuri che sia valutato correttamente dal computer.

Scripting in visual basic - Operatori logici: TestOr.vbs

Vediamo invece come funziona l’operatore Or: la sua “traduzione” in italiano è che “almeno uno dei due valori (“operatori”, in gergo) dell’espressione” sia vero.
Attenzione: “almeno uno dei due valori” vuol dire che l’espressione è vera anche se entrambe sono vere; facendo una tabella come quella precedente possiamo visualizzare la tabella avremo:

Una tabella con gli operatori logigi booleani per l'or
Anche in questo caso un esempio pratico potrà essere chiarificatore… creiamo un nuovo programma TestOr.vbs

'-------------------------------
' Name: TestOr.vbs
' Author: Jeff Skyrunner
' Date: 22/06/10
' Desc: Risponde "Vero" se almeno uno dei due valori inseriti
' dall'utente è strettamente maggiori di 5
'------------------------------


' Primo valore
iPrimoValore = InputBox("Scrivi il primo numero da 1 a 10")

' Secondo valore
iSecondoValore = InputBox("Scrivi il secondo numero da 1 a 10")


if (iPrimoValore > 5) or (iSecondoValore > 5) Then
msgbox "Almeno uno dei due numeri è maggiore di 5"
else
msgbox "Nessuno dei due numeri e' maggiore di 5"
end if

Se proviamo ad eseguirlo ci accorgeremo che il programma entra nella condizione msgbox "Almeno uno dei due numeri è maggiore di 5" solo quando almeno uno dei due numeri (o entrambi) è maggiore di 5, esattamente come ci si aspetta dalla funzione Or.

Scripting in visual basic - Procedure: TestSub.vbs

Uno dei concetti fondamentali da capire nel mondo della programmazione, è che tutti i programmi sono un motivo per risparmiare del tempo, facendo fare al computer qualcosa che non vogliamo/possiamo fare noi; proprio nell’ottica di questa filosofia, un programma come il TestVarType.vbs della scorsa lezione non va bene: che senso ha ripetere due volte lo stesso identico codice? E se volessimo fare una modifica alla select, o ci accorgessimo di un errore? Dovremmo fare le correzioni per due volte, sperando di non sbagliare... e se volessimo ripetere ancora una volta la stessa istruzione? Un altro copia e incolla? Non è la filosofia della programmazione!
In nostro aiuto arrivano le procedure, ovvero la possibilità di scrivere una sola volta il codice, ma ripeterlo quante volte ci serve.

Per capire subito il vantaggio delle procedure, creiamo un nuovo programma TestSub.vbs

SetTipoVariabile(vVariabile)



' -----------------------------------
' Procedura: SetTipoVariabile
' riceve in ingresso una variabile, da il msgbox
' del tipo numerico
' -----------------------------------
Sub SetTipoVariabile(vAltroNome)

' Dichiaro le variabili interne
Dim iTipo
Dim sTipoVariabile

' Ne leggo il nuovo tipo
iTipo = VarType(vAltroNome)

' Visualizzo un messaggio con il numero restituito dalla funzione
Msgbox iTipo

' Uso la funzione Select ... Case per evitare di scrivere
' tantissimi If ... Then ... Else
Select Case iTipo
Case 0
sTipoVariabile = "Vuoto (non inizializzato)"
Case 1
sTipoVariabile = "Null (dato non valido)"
Case 2
sTipoVariabile = "Intero"
Case 3
sTipoVariabile = "Long"
Case 4
sTipoVariabile = "Single"
Case 5
sTipoVariabile = "Double"
Case 6
sTipoVariabile = "Currency"
Case 7
sTipoVariabile = "Date"
Case 8
sTipoVariabile = "String"
Case 9
sTipoVariabile = "Oggetto"
Case 10
sTipoVariabile = "Errore"
Case 11
sTipoVariabile = "Booleano"
Case 12
sTipoVariabile = "Variant"
Case 13
sTipoVariabile = "Oggetto per accesso a dati"
Case 17
sTipoVariabile = "Byte"
Case 8192
sTipoVariabile = "Array"
Case Else
sTipoVariabile = "Tipo non previsto"

End Select

' Visualizzo il tipo dati
msgbox "Il tipo di dato di vVariabile è " & sTipoVariabile

End Sub



Vi sembra familiare? Ebbene si, è il nostro programma TestVarType leggermente migliorato e “potenziato”… se lo lanciate potete vedere che l’effetto è lo stesso, con in più la gestione della stringa come nuovo tipo dati.
Prima di analizzarlo passo passo, andiamo a notare subito la struttura della procedura: l’abbiamo scritta subito dopo la fine del programma principale, ed i suoi “punti salienti” sono:

Sub [nome univoco all’interno del programma] (<eventuali parametri>)

End sub


Il significato è abbastanza ovvio: si scrive Sub e si assegna alla procedura un nome univoco all’interno del programma e nella parentesi si mettono i parametri possibili, lasciando vuoto se non ce ne sono.
Una nota particolare, per quanto veloce, va fatta per i parametri: il nome con cui chiamate il parametro che passate in ingresso indica il nome con cui la variabile sarà conosciuta all’interno della routine… guardiamo la nostra routine per capire meglio:

Sub SetTipoVariabile(vAltroNome)

Possiamo vedere che il parametro di ingresso, come si chiama in gergo, è vAltroNome; all’interno della procedura è lui ad essere analizzato nella stessa maniera in cui era vVariabile nel programma TestVarType.vbs
Non commenteremo il codice all’interno della routine, perché è esattamente lo stesso dell’esempio della lezione precedente, solo con i nomi differenti; guardiamo invece il corpo del programma (o Main, in gergo).

' Dichiarazione delle variabili
Dim vVariabile

' Chiamo la procedura per visualizzare il valore di partenza
' di vVariabile
SetTipoVariabile(vVariabile)

' Assegno un nuovo valore alla variabile
vVariabile = 1

' Chiamo la procedura per visualizzare il nuovo valore di vVariabile
SetTipoVariabile(vVariabile)

Vediamo chiaramente come si fa a chiamare la procedura: basta scrivere il nome della procedura e passare il parametro opportuno, in questo caso vVariabile; il programma quindi intende la chiamata della procedura come: “fai quello che c’è scritto nella procedura SetTipoVariabile ed inizializza vAltroNome con il valore contenuto in vVariabile”.

Piccolo spunto di riflessione: dato che quello che interessa alle procedure è il contenuto di una variabile e non il loro nome, un risultato analogo a quello sopra si sarebbe potuto ottenere in questo modo:

SetTipoVariabile(vVariabile)
SetTipoVariabile(1)
SetTipoVariabile(“1”)

Scripting in visual basic - Funzioni: AreaCerchio.vbs

La differenza sostanziale tra procedure e funzioni, è che le procedure “fanno” qualcosa, mentre le funzioni “restituiscono” un risultato.
Nell’esempio sopra, la procedura SetTipoVariabile prendeva in ingresso una variabile, ne leggeva il tipo e visualizzava un messaggio con la stringa del tipo di dato corrispondente; tuttavia a volte potremmo volere manipolare i dati passati in ingresso, farci delle operazioni sopra.
L’esempio più classico in assoluto è quello dell’area del cerchio: supponiamo di voler permettere all’utente di calcolare l’area di n cerchi; l’algoritmo che vogliamo tradurre è “fino a che l’utente inserisce un valore numerico, calcola l’area del cerchio di raggio corrispondente”.

Creiamo quindi il programma AreaCerchio.vbs

'-------------------------------
' Name: AreaCerchio.vbs
' Author: Jeff Skyrunner
' Date: 24/06/10
' Desc: Calcola l'area del cerchio di raggio imputato
'------------------------------

' Dichiarazione delle variabili
Dim sRaggio
Dim dRaggio
Dim dArea

' Ciclo fino a che l'utente restituisce un valore numerico
Do
' Prendo il raggio come stringa da inputbox
sRaggio = InputBox("Inserire il raggio del cerchio.")

if IsNumeric(sRaggio) Then

' Converto il raggio in un double
dRaggio = CDbl(sRaggio)

' Richiamo la funzione che calcola l'area
dArea = AreaCerchio(dRaggio)

' Restituisco a video il risultato
msgbox "L'area del cerchio corrispondente e' " + CStr(dArea)
Else
' Messaggio di errore: non e' un numeor
msgbox "Il valore inputato non e' un numero, pertanto il programma terminerà"
End if

Loop while IsNumeric(sRaggio)


' -----------------------------------
' Funzione: AreaCerchio
' Riceve in ingresso il raggio del cerchio di cui
' calcolare l'area
' -----------------------------------
Function AreaCerchio(dRaggio)

' Calcolo il valore dell'area
dRetValue = dRaggio * dRaggio * 3.14

' Assegno alla funzione il valore calcolato
AreaCerchio = dRetValue

End Function

Saltiamo le parti che già conosciamo, come il ciclo e la conversione in double, ed andiamo ad analizzare subito la parte saliente, ovvero la funzione; come potete vedere, ci sono due cose che la differenziano dalla procedura: innanzitutto il nome, ovviamente, in quanto invece di essere Sub [Nome univoco] … End Sub, abbiamo un Function [nome univoco] … end function; in secondo luogo (e molto più importante), nelle funzioni deve essere sempre presente l’istruzione NomeFunzione = valore da restituire.
Nel corpo del main, invece, quando chiamiamo una funzione dobbiamo sempre assegnare il suo valore di ritorno ad una variabile, come nel nostro esempio:

' Richiamo la funzione che calcola l'area
dArea = AreaCerchio(dRaggio)

Il resto del codice dovrebbe essere facilmente intuibile, arrivati a questo punto del corso, quindi eviteremo di commentarlo.
Unica nota va fatta sulle conversioni: per correttezza formale abbiamo scritto

' Converto il raggio in un double
dRaggio = CDbl(sRaggio)

' Richiamo la funzione che calcola l'area
dArea = AreaCerchio(dRaggio)

Ma avremmo potuto facilmente scrivere

dArea = Area Cerchio(CDbl(sRaggio))

così come per il valore restituito dalla funzione, che poteva essere “ridotto” in

' Assegno alla funzione il valore calcolato
AreaCerchio = (dRaggio * dRaggio * 3.14)

Ovvero senza dover utilizzare la variabile dRetValue.

A cura di Jeff Skyrunner.