Salta al contenuto principale

Corso visual basic script\operazioni su due numeri

Guido Ruggeri su winguidotecnica,dal 26\12\2009, h. 10.05.

Ora che abbiamo parlato di variabili numeriche, proviamo a
svolgere qualche operazione.
Definiamo due numeri, nelle variabili n1 e n2.
A proposito, piccola parentesi.
I nomi delle variabili possono essere composti da lettere e
numeri, mentre non sono ammessi altri tipi di caratteri:
spazi, punteggiatura, parentesi, eccetera.
Però il nome di una variabile deve cominciare con una
lettera, mai con un numero.
Si può quindi definire le variabili n1 e n2, ma non
potremmo, ad esempio, definire come variabili 1n o 2n.
Inoltre, abbiamo detto, nei nomi delle variabili VBscript
non fa distinzione tra lettere minuscole e maiuscole, mentre
invece in Javascript questa differenza c'è.
Chiusa parentesi.
Dicevo: definiamo due numeri, n1 e n2, e facciamoci sopra le
4 operazioni.
Gli operatori da usare sono:
+ per l'addizione
- per la sottrazione
* per la moltipicazione
/ per la divisione.
L'esercizio da svolgere è il seguente, in 6 righe:

Ed ora, un po' di pubblicità

:

n1 = InputBox("Primo numero:")
n2 = InputBox("Secondo numero:")
MsgBox "Somma = " & n1 + n2
MsgBox "Differenza = " & n1 - n2
MsgBox "Prodotto = " & n1 * n2
MsgBox "Rapporto = " & n1 / n2

Quando andrete ad eseguirlo, vi accorgerete che funziona per
quanto riguarda la differenza, il prodotto e il rapporto.
Mentre sulla sommma...
uhm... sulla somma c'è qualcosa che non va.
Bisognerà ragionarci sopra e capire che cosa.

***
Alessandro Pannocchi.

allora vediamo queste cose qui, che avevo fatto prima di ricevere questa lezione:

prova 1.
Lezione = inputbox("lezione precedente")
Lezione = Lezione + 1
MsgBox "Lezione attuale = " & Lezione

Questo funziona alla perfezione.

prova 2.

base = inputBox("Base = ")
Altezza = InputBox("Altezza = ")
Area = base * altezza
Perimetro = base + base + altezza + altezza
msgbox "Area del rettangolo = " & area
msgbox "Perimetro del rettangolo = " & Perimetro

La somma non va, seppure abbia usato la medesima sintassi della prova precedente
e anche se faccio:

base = inputBox("Base = ")
Altezza = InputBox("Altezza = ")
msgbox "Area del rettangolo = " & base * altezza
msgbox "perimetro = " & base + altezza + base + altezza
perimetro = base + altezza + base + altezza
msgbox base + altezza + base + altezza
msgbox perimetro

Il perimetro non me lo calcola. Notate che ho usato varie sintassi e quindi ho cercato di ottenere lo scopo in vari modi:
ho fatto la somma direttamente nella riga con cui chiamo msgbox, ho creato una variabile perimetro in cui ho inserito la somma e l'ho poi passata a msgbox e infine ho chiamato msgbox senza la scrittta fra virgolette e con solo la variabile, ma senza risultato.

Perchè succede questo?
***

Leggendo i messaggi di oggi, sembra che molti di voi si
siano resi conto di una cosa.
Siamo appena agli inizi, eppure abbiamo già scoperto uno
dei punti deboli di VBScript.
VBScript non ci permette di stabilire che una certa
variabile debba essere destinata a contenere esclusivamente
numeri. Per VBScript, infatti, qualsiasi variabile può
contenere indifferentemente numeri o stringhe.
Però poi ammette che l'operatore di addizione, cioè il
segno +, possa essere usato anche per concatenare le
stringhe, in sostituzione del segno &.
Questo significa che, se non si fa attenzione, si va
incontro alle ambiguità con cui ci siamo scontrati oggi:
si crede di fare un addizione di numeri, e invece si sta
concatenando delle stringhe.
Con altre versioni di Basic ce la saremmo cavata.
Riprendiamo il codice dell'esercizio 6.
Con altre versioni di Basic e, ripeto, non con VBScript,
avremmo risolto semplicemente il problema premettendo a
tutto il resto queste due righe:

Dim n1 as Single
Dim n2 as Single

cosa vuol dire? Vuol dire che io sto dicendo all'interprete:
guarda che in questo programma io userò una variabile, che
chiamerò n1, e che conterrà numeri in precisione
singola, cioè numeri che possono avere anche alcuni
decimali.
Perciò, caro interprete mio, ti dico: tu devi
dimensionarti la variabile n1 come una variabile di tipo
single, cioè numero a precisione singola.
Poi lo stesso ti dico di fare con la variabile n2.
Poi scriveremo:
n1 = InputBox("Primo numero:")
Attenzione: InputBox, sia che ci scriviamo un numero o una
parola, ci restituisce una stringa.
Però l'interprete sa anche che n1 deve essere un numero a
precisione singola.
Perciò che farà? L'interprete prenderà la stringa che
esce dalla funzione InputBox, la convertirà da stringa a
numero, e quindi la memorizzerà nella variabile n1.
Stesso discorso per la variabile n2, quando scriveremo:
n2 = InputBox("Secondo numero:")
Adesso abbiamo n1 ed n2 che sono indubbiamente variabili
numeriche, perché così le abbiamo definite.
Quando ne facciamo la somma, l'interprete sa che è la
somma di due numeri e non il concatenamento di stringhe.
Perciò quando scriveremo:
Msgbox "Somma:" & n1 + n2
non ci saranno equivoci.
Tutto questo, abbiamo detto, si fa in altre versioni di
Basic.
Ma adesso, disgraziatamente, stiamo usando VBScript.
Come ce la caviamo?
VBScript una riga del tipo
Dim n1 as Single
non la accetterebbe.
Quindi scartiamo questa idea.
Vediamo invece se c'è qualche funzione di conversione che
può venirci in soccorso?
Eh si, perché il bello di Basic, in qualsiasi sua
versione, è che è sempre attrezzato per permetterci di
convertire un tipo di variabile in un altro.
Numeri in stringhe, stringhe in numeri.
Ma, prima di andare avanti: vi è chiara la differenza tra
numero e stringa numerica?
Un numero è qualcosa, memorizzato nella memoria del
computer, che ha il valore di un numero.
Ad esempio, il numero 14 è un numero intero che è
superiore a 13 e inferiore a 15, che si può ottenere
facendo 10 + 4, e che sommandogli 3 si ottiene 17.
Una stringa numerica, corrispondente al numero 14, è una
stringa contenente due caratteri: "1" e "4".
Perciò tale stringa è fatta così: "14".
La stringa "14" è la rappresentazione del numero 14
secondo il sistema numerico decimale.
Il numero 14, volendo, avrei potuto rappresentarlo con un
altro tipo di rappresentazione, e avrei ottenuto una stringa
diversa.
Se ad esempio avessi voluto rappresentarlo come numero
romano, avrei ottenuto la stringa: "XIV".
Se avessi voluto rappresentarlo in Braille, avrei ottenuto
una stringa di 3 caratteri: dapprima il simbolo di
segnanumeri, poi il segno della lettera A, e poi il segno
della lettera D.
Questo per dire che potrebbero esserci tanti modi per
rappresentare il numero 14, e farlo con la stringa "14" è
soltanto uno dei modi possibili.
Ma, indipendentemente dal modo che si può scegliere per
rappresentarlo, tutto parte dal numero 14 che ha il valore
di numero 14.
Allora, torniamo a VBScript.
VBScript ci fornisce qualche funzione di conversione che ci
permetta di passare da un numero alla stringa
corrispondente, secondo il sistema numerico decimale, e
viceversa? Certo.
La funzione che serve a noi è: CSng.
CSng converte una stringa in un numero a precisione
semplice.
La sua funzione inversa è: CStr.
CStr converte un numero in una stringa numerica che lo
rappresenta.
Cioè, se io scrivo:
Numero = CSng("14")
anche se "14" l'ho messo tra virgolette, per cui è una
stringa, io ho la certezza che nella variabile Numero ci va
il numero 14, e non la stringa "14".
Viceversa, se io scrivo:
Numero = CStr(14)
anche se 14 stavolta l'ho messo senza virgolette, per cui
è un numero, nella variabile Numero ci troverò la
stringa "14".
Allora riscriviamo l'esercizio 6.
Le prime due righe devono diventare:

n1 = CSng(InputBox("Primo numero:"))
n2 = CSng(InputBox("Secondo numero:"))

Attenzione al gioco delle parentesi. Sia CSng che InputBox
sono funzioni, perciò vogliono il loro parametro tra
parentesi.
Ecco perché dobbiamo aprire una parentesi dopo CSng e
un'altra dopo InputBox, e poi alla fine di ogni riga
dobbiamo chiudere due parentesi.
Dobbiamo cioè stabilire un doppio livello di parentesi.
L'interprete eseguirà per prima ciò che è ha il
livello di parentesi più interno, cioè la funzione
InputBox.
Il risultato di InputBox, che sappiamo essere una stringa,
sarà quindi passato alla funzione CSng che lo convertirà
in numero e memorizzerà il risultato nella variabile.
Se volete evitare di confondervi, potete anche spezzare le
istruzioni in 4 righe, anziché in 2, scrivendo così:

n1 = InputBox("Primo numero")
n1 = CSng(n1)
n2 = InputBox("Secondo numero")
n2 = CSng(n2)

Con l'aggiunta della funzione di conversione CSng, non ci
sono più dubbi che n1 ed n2 acquisiranno i valori
numerici, e non i loro equivalenti sotto forma di stringa.
Perciò, quando andremo a farne la somma, l'interprete
VBScript sa che, trattandosi di numeri, li deve sommare, e
non concatenarli.
Perciò stavolta anche la riga
Msgbox "somma: " & n1 + n2
funzionerà.
Adesso chiediamoci: e perché le altre righe, quelle per la
differenza, il prodotto e la divisione, funzionavano anche
prima?
Perché in quei casi applichiamo operatori che, nel caso di
stringhe, non hanno senso.
Mica si prende la stringa "Guido" e la si moltiplica per la
stringa "Ruggeri"!
Perciò, se applico un operatore di moltiplicazione,
l'interprete sa che le variabili, se non fossero già dei
numeri, le dovrà convertire in numeri prima di eseguire il
prodotto.
Nel caso dell'addizione, invece, rimaneva l'ambiguità,
perché il segno + può avere anche il significato di
concatenamento di stringhe.
Perciò l'interprete, incontrando due stringhe, anziché
convertirle in numeri e sommarle, le concatena.
Ci sarebbero stati meno equivoci se alla Microsoft avessero
deciso di togliere questa ambiguità, riservando il segno +
soltanto alle operazioni di somma tra numeri, e imponendo di
usare soltanto il segno & per concatenare le stringhe.
Non capirò mai perché non l'hanno fatto.
Ma abbiamo imparato un'altra cosa.
Che anche i linguaggi di programmazione, così come tutti
gli altri programmi che usiamo comunemente, hanno i loro
difetti e i loro errori. E' perciò anche importante
conoscerli, capire come aggirarli o come tenerli sotto
controllo.
Adesso riprovate a scrivere l'esercizio 6.
Guido Ruggeri.

***

Facciamo qualche commento sugli esercizi svolti da
Alessandro Pannocchi.

prova 1.

Lezione = inputbox("lezione precedente")
Lezione = Lezione + 1
MsgBox "Lezione attuale = " & Lezione

Questo funziona alla perfezione.
Commento:
Infatti funziona. Dalla prima riga si ottiene la variabile
Lezione sotto forma di stringa, perché da InputBox esce
come tale.
Ma nella seconda riga, a tale stringa viene sommato il
numero 1.
1 è un numero, infatti non è tra virgolette.
L'interprete fa il suo ragionamento e si chiede: cosa
vogliono da me? mi danno una stringa, un numero, e mi
chiedono di sommarli. Allora suppongo che come risultato
vogliano un numero, dato che non sono tutte stringhe e
vogliono usare il segno +.
Allora sapete che faccio? la stringa la converto in numero e
ci aggiungo uno. Il risultato, sotto forma di numero, lo
metto nella variabile Lezione.

prova 2.

base = inputBox("Base = ")
Altezza = InputBox("Altezza = ")
Area = base * altezza
Perimetro = base + base + altezza + altezza
msgbox "Area del rettangolo = " & area
msgbox "Perimetro del rettangolo = " & Perimetro

La somma non va, seppure abbia usato la medesima sintassi
della prova precedente e anche se faccio:
Commento:
In realtà la sintessi sembra simile, ma nella prova
precedente la somma comprendeva qualcosa che era ceramente
un numero, cioè 1.
Stavolta no: è la somma di 4 stringhe, tutte provenienti
da InputBox.
Allora l'interprete si chiede: e adesso cosa vogliono da me?
mi danno 4 stringhe, e si aspettano che io ne faccia la
somma.
Cosa vorranno, che converto le stringhe in numeri e li
sommo, oppure che concateno le stringhe?
Mah, nel dubbio, dato che numeri non ce ne sono, concateno
le stringhe.
Diverso è il discorso per l'area: li c'è una
moltiplicazione, e quella non lascia dubbi all'interprete:
non si fa la moltiplicazione di due stringhe, allora devo
prima convertirle in numeri.
Però, l'interprete tra se e se pensa:
certo che se questi usassero fin dall'inizio una bella
funzione di conversione, io lo saprei una volta per tutte
che vogliono lavorare con dei numeri, e non dovrei
scervellarmi tutte le volte a capire che cosa hanno per la
testa, se vogliono stringhe o numeri.
Ma questi qua non hanno mai sentito parlare della funzione
CSng? ma chi è quell'imbranato che gli insegna a
programmare, possibile che non gli abbia detto niente?
Insomma, un po' di rispetto anche per un povero interprete
VBScript! datemi istruzioni precise, e io vi darò
risultati precisi.

Guido Ruggeri.

***
d.

credo di capire, che una variabile associata a
InputBox possa solo restituire stringhe, ma non
considerare l'immissione di un numero come valore
aritmetico. ,

Chiedo scusa se ho detto una bestialità, ma è quello che
ho capito finora.

Risposta:
E invece ci hai proprio azzeccato.
Da qui l'importanza dell'uso delle funzioni di conversione,
in modo da sapere sempre se stiamo lavorando con stringhe o
con numeri.
L'interprete di VBScript, come abbiamo detto, ha una certa
capacità di capirlo da solo e di prendere le decisioni che
ritiene opportune.
Ma può anche sbagliare, inpterpretando male ciò che noi
avremmo voluto, e quindi darci stringhe quando avremmo
voluto numeri, o viceversa.
Allora è meglio non dare adito a equivoci: ci sono le
funzioni di conversione, usiamole in modo da essere sicuri
che le stringhe siano stringhe e i numeri siano numeri.
Meglio usarle anche quando non servirebbero, piutosto che
rischiare di non usarle quando servono.
Basta scrivere CSng e ci siamo tolti il pensiero.

***
alessandro ricotta.
ho svolto l'esercizio con le modifiche che tu ci hai detto di fare, e
cioè ho utilizzato la funzione CSNG per convertire le stringhe numeriche
restituite dalla funzione InputBox in numeri a precisione singola.
Ecco il testo dell'esercizio:
n1 = CSng(InputBox("Primo numero:"))
n2 = CSng(InputBox("Secondo numero:"))
MsgBox "Somma = " & n1 + n2
MsgBox "Differenza = " & n1 - n2
MsgBox "Prodotto = " & n1 * n2
MsgBox "Rapporto = " & n1 / n2
Adesso tutto OK, anche la somma viene eseguita correttamente, perchè
l'interprete sa inequivocabilmente che deve sommare due numeri.
Quindi quando ho scritto 5 nel campo del primo numero e 4 nel campo del
secondo, mi è apparso come risultato 9, come desideravo.
Ma cosa è successo quando io ho per gioco scritto nel campo del primo
numero una stringa contenente anche lettere ("primo numero 4") anzicchè
solo numeri?
Mannaggia! L'interprete si è bloccato visualizzando un messaggio
d'errore che mi notificava che la funzione CSNG non poteva convertire i
dati contenuti nella variabile N1 poichè di un tipo non corrispondente!
Ecco il messaggio d'errore:
Script: C:\Documents and
Settings\Administrator\Documenti\VBScript\calcoli.vbs
Riga: 1
Carattere: 1
Errore: Tipo non corrispondente: 'CSng'
Codice: 800A000D
Origine: Errore di run-time di Microsoft VBScript

---------------------------
OK
A mio avviso un buon programmatore dovrebbe quindi essere in grado di
prevedere tutti i possibili incidenti che potrebbero capitare durante
l'esecuzione di un programma.
In questo caso, per evitare il messaggio d'errore e la conseguente
interruzione dell'esecuzione dello script, occorrerebbe introdurre una
procedura intelligente in grado di valutare se i dati contenuti
all'interno delle variabili "n1" ed "n2" siano effettivamente stringhe
numeriche e in caso affermativo farli processare dalla funzione CSNG
oppure avvisare l'utente che deve digitare solo numeri tornando indietro
nell'esecuzione dello script e riprendendo dal punto in cui si è
generato l'errore permettendogli di reinserirli negli appositi campi.
Guido Ruggeri.
Hai evidenziato un'esigenza importante, quella di validare i
dati immessi dall'utente.
Coi prossimi esercizi ci arriveremo presto.
Nota però quello che hai scritto. Riporto le tue esatte
parole:
"valutare se"
"e in caso affermativo fare"
"oppure".
Infatti è proprio qui che dobbiamo arrivare: valutare e
prendere le decisioni secondo i casi.
Ma prima di arrivarci, dovremo ancora approfondire qualcosa
sui tipi di variabile.

d.
Resta però in piedi la domanda
che avevo fatto in un messaggio precedente: perchè questo
listato funziona?
Lezione = inputbox("lezione precedente")
Lezione = Lezione + 1
MsgBox "Lezione attuale = " & Lezione

Risposta:
Funziona perché nella seconda riga hai aggiunto alla
variabile Lezione, che prima era una stringa, il numero 1.
E 1 è inequivocabilmente un numero, dato che non lo hai
messo tra virgolette.
L'interprete, per poter fare quell'operazione, ha quindi
dovuto convertire Lezione in numero.
Il risultato della somma, che a questo punto è un numero,
viene di nuovo collocato nella variabile Lezione, che da
questo punto in poi contiene un numero e non più una
stringa.

***
d.

Ciao Guido ho fatto l'esericizio e riesce senzza problemi ma mi sono posta
una domanda alla quale non riesco a dare una risposta.
in realtà forse con il nostro esercizio di programmazione ci entra poco ma
vorrei capire meglio una cosa.
noi facciamo l'esercizio e mettiamo i numeri e il programma è capace di fare
le sue addizioni, sottrazioni moltiplicazioni e divisioni e al termine
dell'esercizio riesce a fornirci i risultati, ma in questo caso vb script a
cosa si appoggia per fare i suoi conti alla calcolatrice di windows o al
sistema binario del computer.
Magari ho detto delle cose imprecise però e un dubbio che mi è venuto
appena fatto l'esercizio e ho preferito chiedere chiarimenti a riguardo, è
vero che non si tratta di programmazione vera e propria ma la mia domanda è
legata comunque ad operazioni che il computer deve compiere autonomamente.

r.
Donato Taddei.
ci provo io a rispondere al tuo quesito.

si appoggia a una sezione del sistema operativo, un file con estensione .dll
che guarda caso si chiama vbscript.dll.
Quel file vbscript.dll ha tutte le funzioni per interpretare ed eseguire ciò
che noi scriviamo,
per poter obbedire ai nostri ordini, compresi quelli di fare le somme.
Quando noi eseguiamo lo script, il sistema operativo chiama, regolandosi
sulla estensione vbs,
un programma chiamato "windows script host", o se vogliamo "ospite, gestore
degli script di windows"
il quale a sua volta carica la libreria, o collezione di fuzioni, chiamata
vbscript.dll dicendogli:
"c'è posta per te" e gli consegna il nostro script.
Questa lo esamina e se trova strafalcioni,
ritorna a windows script host un codice di errore, e questo ce lo notifica
quando cazziamo.
Se va bene, esamina la nostra lista degli ordini e se li
prepara,trasformandole in isturzioni macchina.
nel far questo, poi, come in un sistema di scatole cinesi, ciascuna delle
funzioni e procedure contenute in questa collezione chiamata vbscript.dll a
sua volta utilizzi molte o potenzialmente quasi tutte le altre funzioni del
sistema operativo , come del resto tutti i programmi,
p un altro paio di maniche, che esula dalle preoccupazioni di chi pasticcia
un programmetto.
Tuttavia sanno tutti che alla fine della fiera sono bit acdesi o spenti gli
elementi costitutivi di cui è costituito un sistema informatico digitale.
Quello è l'unico linguaggio che la macchina capisce e che sarebbe
enormemente snervante e ormai eterno per l'uomo.
Perciò, a differenza dei primi computer che erano incredibilmente primitivi,
o delle addizionatrici meccaniche,
man mano sono nati linguaggi di programmazione sempre più vicino al
linguaggio umano,
in cui, a partire da parole del linguaggio umano, tramite appunto
l'interprete o il compilatore, alla fin fine il risultato finisce in una
serie infinita di 1 e di 0.
Il fatto è che i linguaggi sono nati per lo più in ambiente anglofono per
cui a noialtri risultano un po ostrogoi.
Non è escluso che se il vbscript lo avessero inventato in Italia avresti
avuto
FinestraEditazione invece di InputBox
e FinestraDiDialogo o finestramessaggio per MsgBox, come ci recitano gli
screen-reader.

Guido Ruggeri.
Verso la metà degli anni '90 effettivamente uscì una
versione di Microsoft Excel, la cui edizione italiana
includeva un linguaggio di programmazione tipo Visual Basic,
ma in italiano, e le istruzioni erano tradotte proprio come
dici tu.
Era un vero disastro. Forse poteva andare bene per chi
cominciava a programmare lì per la prima volta in vita
sua, ma per chiunque avesse già programmato con un
linguaggio ordinario in inglese, e ormai ci si era abituato,
era un vero disastro: non ci si capiva niente.
La cosa, infatti, non ha avuto successo e non è durata.

***
Antonio De Angelis.

be, anche se poca cosa .
mi viene da ridere, ma un piccolo rudimento di integrazione funzione in wg penso di averlo creato.
convertitore euro lire che manca nella calcolatrice di wg.
so che e na cavolata ma bello bello avere l'illusione di aver creato un piccolo programmino.
Euro = csng(inputbox("Inserire L'importo in Euro"))
Cambio = csng(1936.27)
msgbox " Il Cambio in Lire è: " & Euro * cambio
Lire = csng(inputbox("Inserire L'importo in Lire"))
Cambio = csng(1936.27)
msgbox " Il Cambio in Euro è: " & Lire / cambio

e giusto capo o sbagliato così?
grazie a roberto per averdmi dato l'imput.

Guido Ruggeri.

Questo è uno dei casi in cui non c'è alcun pericolo ad
omettere la funzione di conversione CSng quando assegni il
valore alla variabile Cambio.
Infatti è sufficiente scrivere:
Cambio = 1936.27
Trattandosi della assegnazione di un valore che certamente
non è una stringa, l'interprete non può equivocare.
Se poi li consideri come due programmi separati, va bene
così. Altrimenti, se vuole essere un unico programma, non
serve ripetere l'assegnazione del valore di Cambio, basta
una volta sola.