Fortran

210
l " I ,Il I ,l , ( i l. GIANNI AGUZZI MARIA GRAZIA GASPARO MARIA MACCONI FORTRAN 77 Uno strumento per il calcolo scientifico PITAGORA EDITRICE BOLOGNA

description

manuale FORTRAN

Transcript of Fortran

Page 1: Fortran

~

l

"

I,Il

I

, l

, (i •

l.

GIANNI AGUZZIMARIA GRAZIA GASPARO

MARIA MACCONI

FORTRAN 77Uno strumento

per il calcolo scientifico

PITAGORA EDITRICE BOLOGNA

Page 2: Fortran

PARTE J - CONCETTI FONDAMENTALI

I. GLI ALGORITMI E LA LORO DESCRIZIONE

1.1. Introduzione............................................ 31.2. Il linguaggio dei diagrammi a blocchi. . . . . . 91.3. Il linguaggio delle funzioni ricorsive . . . . . . . . . . . . . . . . . . . . . . . . . 14

000355

AIiIUUI/Gup."oM.cc:onl

FORTRAMnPIi.gora Edit.

ISBN 88-371-0378-6

© Copyright 1987 Pitagore Editrice s.r.l., Via del Legatore 3, BolognaTutti i diritti riservati Riproduzione vietata.

Composizione e stampa: Tecnoprint. ViD del Legatore 3, BolognaCodice: 21/211

..

Indice

Prefazione . . . . . - - . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .

2. DAL LINGUAGGIO MACCHINA ALLA REALIZZAZIONE DEI LINGUAGGISIMBOLICI

2.1. Introduzione .2.2. Unità hardware di un elaboratore convenzionale .2.3. 11 linguaggio macchina .2.4. I linguaggi simbolici .2.5. La realizzazione di un linguaggio simbolico .2.6. Il sistema operativo - .

3. RAPPRESENTAZIONE DEI NUMERI

3.1. Numeri interi .3.2. Numeri reali. . . . . . . . . . . . . . . . . . . . . . . .3.3. Rappresentazione finita ed errori di arrotondamento .

PARTE JJ • IL FORTRAN 77

4. IL LINGUAGGIO FORTRAN

4.1. Introduzione .4.2. Alfabeto ···4.3. Costanti, nomi simbolici e parole chiave .4.4. Frasi eseguibili e non eseguibili. .4.5. Etichette - .4.6. Il formato delle linee .

5. COSTANTI E VARIABILI: ELEMENTI FONDAMENTALI DI OGNI ISTRUZIONE

5.1. Le costanti ed il loro tipo .

XI

212223252830

333739

474848494950

53

Page 3: Fortran

f

VI VII

6.

7.

5.2. Le variabili ed il loro tipo .5.3. L'istruzione IMPUCIT .

LE ESPRESSIONI

6.1. Espressioni aritmetiche .6.2. Espressioni reiazionali .6.3. Espressioni logiche .6.4. Espressioni costanti .

Esercizi .

LA FRASE DI ASSEGNAZIONE

7.1. Introduzione ·7.2. Assegnazione aritmetica .7.3. Assegnazione logica .

Esercizi .

5658

61767779

80

838386

87

11. LE VARIABILI DIMENSIONATE

Il.1. Introduzione .Il.2. Nomi di variabili dimensionate e istruzione DlMENSION .Il.3. Nomi di elementi di variabile dimensionata .IlA. Disposizione in memoria degli elementi di una variabile dimensionata .11.5. Esempi di utilizzazione delle variabili dimensionate .

Esercizi .

12. ELABORAZIONE DELLE INFORMAZIONI DI TIPO CARATTERE

12.1. Memorizzazione dei caratteri .12.2. Le costanti e le variabili di tipo carattere .12.3. Sottostringhe ed espressioni carattere .12A. Assegnazione fra stringhe di caratteri. .12.5. Lettura e scrittura dei dati di tipo carattere .12.6. Confronto tra espressioni carattere .12.7. Funzioni intrinseche perla manipolazione dei caratteri .

Esercizi .

151153156160164

171

173174178180183185187

1918. ALCUNI SEMPLICI PROGRAMMI

8.1. Introduzione .8.2. Frasi di ingresso/uscita guidate dalla lista .8.3. Le istruzioni PROGRAM, STOP e END .8A. L'istruzione PARAMETER .8.5. Altri esempi .

Esercizi .

9. SCELTE E DECISIONI

9.1. Controllo esplicito dell'esecuzione: !'istruzione GOTO-incondizionato .9.2. Costrutto IF ·THEN·ELSE .9.3. Strutture decisionali annidate .9 A. Strutture decisionali concatenate .9.5. Riepilogo .9.6. If-logico: una struttura particolarmente semplice .9.7. GOTO-calcolato .9.8. IF-aritmetico .

Esercizi .

lO. CICLI

10.1. Strutture di ripetizione .10.2. Istruzione DO .10.3. Il cìclo-Do .10.4. Cicli e strutture decisionali .10.5. Trasferimento ad istruzioni fuori del rango .10.6. Cicli-Dì) annidati. .

Esercizi .

8989929597

98

101102105111114116120121

121

125132133140143145

148

13. OPERAZIONI DIINGRESSO/USCITA CON FORMATO

13.1. Alcune considerazioni sulle frasi di ingresso/uscita guidate dalla lista .13.2. Specificazioni di formato .13.3. Rappresentazione dei dati numerici sui records di l/O .BA. Il descrittore Iw per dati di tipo intero .13.5. I descrittori Fw.d, Ew.d, DW.d per dati di tipo reale e doppia precisione .13.6. I descrittori ripetibili per dati di tipo complesso .13.7. I descrittori ripetibili per dati di tipo carattere .13.8. Istruzioni di ingresso/uscita con formato relative ai mezzi standard .13.9. Interazione fra lista di ingresso/uscita e specificazione di formato .13.10. Controllo della spaziatura verticale su stampante .13.11. I principali descrittori non ripetibili .13.12. La lista di ingresso/uscita .13.13. Le frasi READ (u, f) e WRITE (u, f) .13.14. Esempi di stampa di variabili dimensionate .13.15. Altri descrittori .

Esercizi....................................................

]4. DEFINIZIONE E UTILIZZAZIONE DEI SOTTOPROGRAMMI

14.1. Programma principale e sottoprogrammi .14.2. La prima istruzione di un sottoprogramma .14.3. Il corpo di un sottoprogramrna e l'istruzione RETURN .14.4. I sottoprograrnmì SUBROUTINE e la frase CALL .14.5. I sottoprogrammi FUNCTION .14.6. Le funzioni definite da una frase .14.7. Le funzioni intrinseche .

Esercizi .

193194197198199202203205208214215219222223

228

234

239243244245252259261

271

Page 4: Fortran

VIIIIX

381384389392

395397

Differenze con il subset 1anguage .Prìncipali differenze fra il FORTRAN 77 e il FORTRAN 66 .Ordinamento delle istruzioni F77 .La codifica dei caratteri in ASCII e EBCDlè' ........................

APPENDICI

Al.A2.A3.A4.

Bibliograflll .Indiceanalitim ............................ ...................... .

15. ARGOMENTI MUTI ED ARGOMENTI ATTUALI

15.1. Associazione tra argomenti muti ed argomenti attuali. 27515.2. Le variabili non dimensionate come argomenti muti " 27515.3. Le variabili dimensionate come argomenti muti. " 27715.4. Dimensionamento variabile e dimensionamento indefinito " 28015.5. Argomenti muti di tipo carattere. . . . . . . . . . . . . . . . . . . . . . . . . . . . .. 28915.6. l nomi di sottoprogrammi come argomenti muti. Le frasi EXTERNAL e

INTRINSIC " 29215.7. Asterischi come argomenti muti. . . . . . . . . . . . . . . . . . . . . . . . . . . . . .. 299

Esercizi. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .. 301

16. USO FLESSmlLE DELLA MEMORIA

16.1. L'istruzione COMMON. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .. 30716.2. Utilizzazione dei blocchi COMMON " 30916.3. L'istruzione EQUlVAlENCE " 31616.4. Interazione fra istruzioni COMMON ed EQUIVALENCE " 31916.5. La frase DATA 32116.6. Sottoprogrammi BLOCK DATA " 325

Esercizi " 327

17. USO FLESSmlLEDEI SOTTOPROGRAMMI

17.1. Punti di ingresso secondari: l'istruzione ENTRY " 33117.2. Punti di ingresso secondari di un sottoprogramma SUBROUTINE " 33417.3. Punti di ingresso secondari di un sottoprogramma FUNCnON " 33717.4. Le variabili interne di un sottoprogramma e l'istruzione SAVE " 34117.5. I blocchi COMMON etichettati e l'istruzione SAVE " 347

Esercizi. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .. 349

18. TRATTAMENTO DEI FILES

18.1. Introduzione..................................... 35118.2. Records e files . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .. 35118.3. La forma generale delle frasi di I{O . . . . . . . . . . . . . . . . . . . . . . . 35518.4. Connessione di un file esterno: frasi OPEN e CLOSE . . . . . . . . . . . . . . 35918.5. Frasi di posizionamento: BACKSPACE e REWIND . . . . . . . . . . . . . . 36518.6. Files ad accesso diretto. . . . . . . . . . . . . . . . . . . . . . . . . . . 36818.7. Indagine sulle unità dillO e sui files: frase INQUIRE . . . . . . . . . . . . . . 37118.8. Files interni. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 375

Esercizi. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 377

I\ \ ~

Page 5: Fortran

Prefazione

In questo volume è descritta l'ultima versione del linguaggio FORTRAN nota

come FORTRAN 77 e definita nel documento X3.9.1978 dell'A m erican National

Standard Institute. Questa versione, ormai disponibile nella maggior parte degli

elaboratori elettronici, costituisce un importante strumento per la realizzazione

di programmi direttamente utilizzabili su sistemi di calcolo anche molto diversi

tra loro.

E' noto che le principali applicazioni del linguaggio FORTRAN sono di tipo

numerico ed è per questo motivo che il testo è rivolto principalmente a chiun­

que abbia interesse ad utilizzare un elaboratore per risolvere problemi di natura

scientifica o tecnica. Va però osservato che il FORTRAN 77 allarga le possibi­

lità di applicazioni anche a problemi di carattere gestionale in quanto permette

sia la manipolazione dei caratteri che l'utilizzazione di [iles di dati ad accessodiretto. In ogni caso, una corretta utilizzazione del FORTRAN non può prescinde­

re dalla conoscenza di alcuni prerequisiti che, secondo gli autori, devono far parte

del bagaglio culturale di chiunque utilizzi Wl elaboratore elettronico. Per questo

il testo è diviso in due parti. La prima parte può non interessare il lettore già

esperto nell'uso dei linguaggi di programmazione ed è costituita da tre capitoli

nei quali si danno le nozioni di base su alcuni argomenti fondamentali quali gli

algoritmi e la loro descrizione (capitolo 1), la struttura degli elaboratori elet­

tronici e la realizzazione dei linguaggi simbolici (capitolo 2), le modalità di rap­

presentazione dei numeri e gli errori di arrotondamento (capitolo 3J.La descrizione del FORTRAN, oggetto della seconda parte del libro, è orga­

nizzata in modo da fornire il più rapidamente possibile gli strumenti necessari per

poter scrivere alcuni semplici programmi. Per questo, dopo aver descritto nei

capitoli 4, 5 e 6 gli elementi di base del linguaggio, le modalità di definizione

delle variabili e delle costanti e le caratteristiche della formalizzazione e valuta­

zione delle espressioni, nei capitoli 7 e 8 vengono presentate le istruzioni che

consentono di scrivere alcuni programmi completi comprendenti frasi di asse­

gnazione, di lettura dei dati e scrittura dei risultati.

Page 6: Fortran

...

XII

Nei due capitoli successivi vengono analizzati i costrutti che permettono di

realizzare in FORTRAN gli schemi teorici che stanno alla base della programma­zione strutturata: nel capitolo 9 viene presentato il costrutto decisionale IF­

THEN-ELSE e nel capitolo lO quello di ripetizione controllato dalla istruzione DO.

Nel capitolo Il sono descritte le modalità di utilizzazione delle variabili di­mensionate mediante le quali è possibile tradurre in FORTRAN la notazione vet­

toriate comunemente usata nei problemi di natura scientifica, mentre il capitolo

12 è dedicato alla descrizione delle possibilità offerte dal FORTRAN 77 per la

manipolazione di stringhe di caratteri.

Nel capitolo 13 vengono presentate le operazioni di ingresso/uscita con forma­

to. Questo argomento, estremamente vario in quanto il FOR TRAN 77 offre al

riguardo moltissime possibilità. viene affrontato cercando di fornire prima le

nozioni elementari e poi quelle più sofisricate in modo da distinguere le cono­

scenze basilari da quelle necessarie solo per particolari operazioni di ingres­

so/uscita.Nei capitoli 14, 15. 16 e 17 si trattano gli argomenti legati all'uso dei sottopro­

grammi ovvero alla possibilità di decomporre un programma in più unità ciascuna

delle quali può essere scritta e compilata in modo autonomo. Il testo si chiudecon il capitolo 18 nel quale vengono descritti il trattamento e la gestione deifiles di dati.

Nel testo l'iene rigorosamente descritta la sintassi delle istruzioni FORTRAN,·il significato e l'uso di ogni istruzione è inoltre spiegato tramite numerosi e­

sempi. Sono anche sottolineate le differenze rispetto al FORTRAN 66 in modo

da rendere il libro utile a chi abbia a disposizione un sistema di calcolo che realiz­za una versione del FORTRAN precedente al FORTRAN 77. Ogni capitolo è

accompagnato da esercizi che permettono al lettore di verificare immediata­

mente il lil'ella di apprendimento raggiunto.La stesura dei capitoli 2, 8, 16, 18 è stata curata dal primo autore che si è

anche occupato del trattamento della ricorsivuà (§ 1.3) e delle funzioni intrin­

seche (§ 14.5). Il pro! Aguzzi si è anche assunto il compito di verificare la

correttezza di tutti i programmi presentati nel testo, utilizzando a tale scopo un

elaboratore IBM PC AT con compilatore PROFORT 77 e un elaboratore VAX

11/730 con compilatore VAX-ll FORTRAN V 3.0. Il secondo autore ha curato

la stesura dei capitoli 1,4,11,13,14,15,17, mentre il terzo autore ha curato

quella dei rimanenti capitoli.L'impostazione usata in questo testo è stata seguita per insegnare il linguaggio

FORTRAN agli studenti dei corsi di Calcolo numerico tenuti a Firenze nel Corsodi laurea in Matematica e nella Facoltà di Ingegneria, coinvolgendo, oltre agli

autori, i pro! F. Fontanella, A. Pasquali, P. Costantini e la d.ssa R. Morandi.ai quali vanno i più sinceri ringraziamenti per i numerosi e utilissimi consiglie suggerimenti.

IConcetti fondamentali

Page 7: Fortran

Il,

1Gli algoritmie la loro descrizione

1.1. Introduzione

Con il termine al~?!~tl1lfL~i intende una successione finita di istruzioni, asse­gnate in modo non ambiguo, tali che la loro esecuzione consenta di passare,

in un tempo finito, da una assegnata situazione iniziale (problema) ad una situa­

zione finale (risultato). L'esecuzione delle istruzioni di un algoritmo presuppone

un insieme di dati che individuano, nella classe di problemi risolubili mediante

l'algoritmo, il problema da risolvere e la disponibilità~ di un esecutore capace

di effettuare, nell'ordine prestabilito, le azioni indicate dalle istruzioni. AI termine

dell'esecuzione si ottiene il rts!!!!!!~ che deve essere univocamente determinato

dall'insieme dei dati. Da quanto detto segue che un algoritmo non è altro che

la descrizione del calcolo di una funzione che associa, in modo univoco, il risul­

tato all'insieme dei dati.

Nella stesura di un algoritmo devono essere tenute ben presenti le capacità

dell'esecutore per evitare istruzioni che non possono essere eseguite. In altri

termini, un algoritmo deve essere costituito da una successione di istruzioni

realizzabili mediante operazioni che l'esecutore sa eseguire (operazioni primitive).

L'ordine in cui devono essere eseguite queste operazioni, detto anche [lusso, è

di solito quello sequenziale a meno di esplicite indicazioni contenute nelle istru­

zioni stesse. Gli esempi seguenti mostrano come sia possibile risolvere alcuni

problemi matematici supponendo di avere a disposizione un esecutore che possa

eseguire istruzioni formulate in lingua italiana ed in particolare sappia leggere,scrivere, eseguire le operazioni aritmetiche e confrontare tra loro due numeri.

La numerazione progressiva che precede la descrizione di ciascuna istruzione

definisce, visualizzandolo, il flusso sequenziale dell'algoritm o. Inoltre l'istru­

zione «poni v = e» significa che, una volta determinato il valore di e, lo si indica

con il simbolo ~'. Ogni istruzione di questo tipo verrà chiamata nel seguito istru­zione di assegnazione.

Esempio 1.1. Si vuoI determinare il più piccolo di una tema di valori.

Page 8: Fortran

4

Indicati con al' a2

e a3

i tre numeri assegnati, è possibile ottenere il risultato

r = min {al' a2, a

3} eseguendo quanto specificato nel seguente algoritmo:

Algoritmo 1.1.

1. Leggi: al' a2, a32. confronta al con a2· Se al > ~ allora: poni m = a2 ed esegui 3.

altrimenti: poni m = al ed esegui 3.

3. confronta m con a3 · Se m> a3 allora: poni m = a3 ed esegui 4.altrimenti: esegui 4.

4. poni r = m5. scrivi: r

6. stop.La prima istruzione impone l'acquisizione dei dati del problema. Supponendo

che essi siano i valori {3, 2, l} l'esecuzione delle successive istruzioni avviene nel

modo seguente:• si confronta 3 con 2 e, siccome 3> 2, si ha m = 2;• si confronta m con a3 ovvero 2 con 1 e, siccome 2 > 1, si ha m = 1;• il risultato r è posto uguale al valore di m ovvero, in questo caso, r = 1.

Se la tema di valori fosse stata {3, 2, 4} il confronto previsto dall'istruzione 3.

tra m = 2 ed a3

= 4 non avrebbe provocato nessuna modificazione di m ed il

risultato sarebbe stato r = 2.Il significato delle istruzioni 5. e 6. è intuitivo: la prima fornisce il risultato

r dell'algoritmo mentre la seconda impone la fine dell'esecuzione delle istruzioni.

Si osservi che l'algoritmo 1.1 è applicabile ad una qualunque tema di valori

in quanto è stato scritto indipendentemente dai dati effettivi del singolo pro­

blema.

Esempio 1.2. Si vuol determinare il più piccolo tra n numeri reali.Indicati con a a

2a gli n valori assegnati, il risultato r = min {ak }l' , ..., n l .. k" n

pUÒ essere ottenuto con un algoritmo basato, come quello dell'esempio pre-

cedente su confronti successivi tra il valore m = min {~} ed ai con, l .. k" i - l

2 ~ i ~ n. Il numero di confronti necessari per determinare il risultato dipende

ovviamente da n in quanto, fissato il primo valore di m (m = al)' il risultato rè ottenuto dopo aver ripetuto n - l volte l'operazione di confronto. Le consi­

derazioni fatte permettono di scrivere il seguente algoritmo che prevede tra i datidel problema oltre ai valori al' a2, ..., a

nanche il valore di n; esso è quindi appli­

cabile ad una qualsiasi n-pla di valori, qualunque sia il numero n, n > l, di ele­

menti che la compongono.

5

Algoritmo 1.2.

I. Leggi: n; al' a2, •.• , an

2. poni m = al;3. ripeti per i = 2, 3, ..., n:

3.1. confronta m con ai' Se m> ai allora: poni m = ai ed esegui 3.2altrimenti: esegui 3.2

3.2. continua il procedimento ripetitivo

4. poni r = m

5. scrivi: r

6. stop.

In questo algoritmo e nel seguito le istruzioni che devono essere ripetute

sono scritte più a destra delle altre ed evidenziate da una doppia numerazione.

Applichiamo l'algoritmo 1.2 per determinare r = min {6, 3, 3, J}. In questo

caso n = 4, al = 6, a2 = 3, a3 = 3, a4 = l costituiscono i dati del problema che

vengono acquisiti con l'esecuzione della prima istruzione. L'istruzione successiva

inizializza il valore di m imponendo m = 6. Le istruzioni 3.1 e 3.2 vengono quindi

eseguite in sequenza tre volte. La prima volta si pone i = 2 ed il confronto pre­

visto dall'istruzione 3.1 avviene tra m ed a2 ovvero tra 6 e 3; siccome 6 > 3si modifica il valore di m che diventa 3. La seconda volta si ha i = 3 e, siccome

m ed ~ hanno lo stesso valore, si effettua un altro confronto senza modificare m.Il confronto successivo, l'ultimo, avviene tra m ed a

4ovvero fra 3 ed l e, siccome

3 > l, si ha m = I. Avendo esaurito il numero di ripetizioni previste dalla istru­zione 3. il valore di m rappresenta il risultato ed infatti, con l'istruzione 4., sipone r = m ovvero r = l. Le istruzioni 5. e 6. hanno il significato già visto nel­

l'algoritmo 1.1.Si osservi che, specificando n = 3, l'algoritmo 1.2 permette di risolvere il pro­

blema posto nell'esempio precedente; esso è quindi più generale dell'algoritmo

1.1.

Esempio 1.3. Assegnati n numeri reali se ne vuol calcolare la somma.

Indichiamo con al' a2, ..., an gli Il valori da sommare. Supponendo n> 2, iln

risultato r = 1: a è ottenuto eseguendo successive operazioni di somma tra duei= l l

addendi nel modo seguente: detto s il risultato della somma tra al ed a2 ad esso si

aggiunge a3

ovvero si esegue l'operazione: s + a)' Indicato ancora 1:011 s 11 risul­

tato di questa operazione ad esso possiamo sommare a4

e così via fino ad esau­

rire tutto il numero di addendi. Basandosi su questo procedimento si può allora

scrivere il seguente algoritmo in cui, ripetiamo, si suppone n> 2.

Page 9: Fortran

I

~

I

6

Algoritmo 1.3.1. Leggi: n; al' a2, ... , an

2. poni s = al + a23. ripeti per i = 3, 4, ... , n:

3.1. poni m = s + ai

3.2. poni s = m

4. poni r = s

5. scrivi: r

6. stop.

nSi osservi che, qualunque sia n, la quantità r = ~ a. può essere pensata come

i= l I n

il risultato della somma di due addendi, uno uguale a zero e l'altro uguale a ~ ai'i=l

Usando questa osservazione è allora possibile scrivere un algoritmo più generale

del precedente in quanto applicabile qualunque sia il numero n di addendi.

Algoritmo 1.4.

l. Leggi: n; al' a2, •.• , an

2. poni s = O

3. ripeti per i = I, 2, ... , n:

3. 1.poni m = s + ai

3.2.poni s = m

4. poni r = s

5. scrivi: r

6. stop.

Esempio 1.4. Assegnati n numeri reali se ne vuoI calcolare il prodotto.

Se al' a2' ... , an

rappresentano i valori dati, considerazioni analoghe a quelle

svolte nell'esempio precedente permettono di scrivere il seguente algoritmo ap-n

plicabile per calcolare r = n a. qualunque sia il numero n dei fattori.i= l I

Algoritmo 1.5.

l. Leggi: n; al' a2, .• " an

2. poni p = l

3. ripeti per i = 1,2, ... , n:

3.l.poni m = p' ai

3.2.poni p = m

4. poni r = p

5. scrivi: r

6. stop.

7

Esempio 1.5. Si vuoi determinare il massimo ed il minimo fra n numeri reali as­

segnati.Indicati con a) . a2•... , a

ngli n numeri dati si tratta di scrivere un algoritmo

il cui risultato è costituito dalla coppia di valori R = max {a i ed r = min {a l·l <;; i <; n I l <; i .. n I

Tenendo presente le considerazioni svolte nell'esempio 1.2 ed osservando che R

può essere determinato con un procedimento analogo a quello descritto per il

calcolo di r, si giunge al seguente algoritmo.

Algoritmo 1.6.

l. Leggi: n; al' a2, .•. , an

2. poni m = al

3. ripeti per i = 2, 3, ... , n:

3.1. confronta m con ai' Se m > ai allora: poni m = ai ed esegui 3.2

altrimenti: esegui 3.2

3.2. continua il procedimento ripetitivo

4. poni r = m

5. scrivi: r

6. poni m = al

7. ripeti per i = 2,3, ... , n:

7.1. confronta m con ai' Se m > ai allora: esegui 7.2

altrimenti: poni m = ai ed esegui 7.2

7.2. continua il procedimento ripetitivo

8. poni R = m

9. scrivi: R

lO. stop.

L'impostazione data al problema ha portato ad un algoritmo chiaramente di­

visibile in due parti: la determinazione di r, che avviene con l'esecuzione delle

prime cinque istruzioni, e quella di R che avviene dalla sesta istruzione in poi.

Si osservi inoltre che per portare a termine questo procedimento sono necessari

2( n - l) confronti e che l'unica differenza, per altro fondamentale, tra la prima

e la seconda parte si presenta al momento del confronto tra m ed ai' Quando non

si abbia interesse a mantenere nettamente distinte la determinazione di R da

quella di r è possibile risolvere lo stesso problema utilizzando un altro algoritmo

che prevede meno confronti del precedente.

Algoritmo l. 7.

l. Leggi: n; al' a2, · . " an

2. poni m = al

3. poni M = al

4. ripeti per i = 2, 3, ... , n:

Page 10: Fortran

8 9

Questo modo di affrontare la soluzione di un problema mediante la scomposi­

zione in sottoproblemi è quello comunemente usato nella pratica e sta alla base

della tecnica nota come programmazione strutturata «(1D.

1.2. II linguaggio dei diagrammi a blocchi

La descrizione discorsiva adottata fino ad ora per la formulazione degli algo­

ritmi è sicuramente la più naturale. Essa, però, può non essere sufficiente a

descrivere con la dovuta chiarezza le azioni che devono essere compiute e sicura­

mente non consente una immediata visualizzazione del flusso dell'algoritmo.

Adoperando opportuni simboli per rappresentare le istruzioni e la loro succes­

sione, è possibile descrivere graficamente un algoritmo mettendone in evidenza

i singoli comandi e le loro interrelazioni. Tale descrizione grafica, detta diagram­ma a blocchi. è realizzata mediante una concatenazione di simboli (blocchi)che, di solito, hanno forma diversa a seconda del tipo di istruzione da essi indi­

cata. Dentro ciascun simbolo vengono poi descritte le azioni che devono essere

compiute dall'esecutore dell'algoritmo. I blocchi più comunemente usati e le

operazioni che essi indicano sono i seguenti:

simbolo terminale. Rappresenta il punto in cui un algo­

ritmo inizia (start) o finisce (stop);)c__

Come si vede anche dall'esempio precedente, la risoluzione di un problema

può essere effettuata mediante algoritmi diversi ciascuno dei quali corrisponde

ad una diversa analisi del problema e del procedimento risolutivo. Si osservi

inoltre che di solito è utile determinare la soluzione di un problema mediante

quella di opportuni sottoproblemi per i quali sia disponibile un algoritmo.

4.1. confronta m con ai' Se m> ai allora: poni m = ai ed esegui 4.3altrimenti: esegui 4.2

4.2. confronta Mcon ai' Se M < ai allora: poni M = ai ed esegui 4.3

altrimenti: esegui 4.3

4.3. continua il procedimento ripetitivo

5. poni r = m

6. poni R = M

7. scrivi: r ed R

8. stop.

Esempio 1.6. Assegnati n numeri reali positivi che indichiamo con al' a2 , ... , an

si vuoI calcolare l'area del quadrato che ha come lato la loro media aritmetica.

Indicata con m la media aritmetica degli n valori dati, il risultato è rappresen­

tato dal valore r = m2. Una prima analisi del problema conduce quindi al seguente

algoritmo:

Algoritmo 1.8.

I. Leggi: n; al' a2, ... , an I n

2. calcola la media aritmetica m =- I: ain i= l

3. poni r = m2

4. scrivi: r

5. stop./

simbolo di direzione. Indica il flusso dell'algoritmo

collegando tra loro tutti i blocchi;

simbolo di ingresso/uscita. Rappresenta il punto in cui

viene acquisito l'insieme dei dati (operazione di ingres­

so) oppure viene fornito il risultato (operazione di u­

scita);

la cui esecuzione presuppone la possibilità di utilizzare un altro algoritmo per cal­

colare il valore m come indicato dall'istruzione 2. Supponendo disponibile l'al­

goritmo che permette di calcolare la somma di n numeri si ottiene la formula­

zione seguente:

Algoritmo 1.9.

I. Leggi: n; al' a2, .•• , ann

2. calcola s = I: aii= l

3. poni m = sin4. poni r = m2

5. scrivi: r6. stop.

Intestazione

simbolo di decisione. Viene usato per indicare un punto

da cui, in base al verificarsi o meno della condizione spe­

cificata al suo interno, è possibile passare all'esecuzione

di parti distinte dell'algoritmo. Se la condizione risulta

vera il flusso procede nella direzione indicata da V, altri­

menti in quella indicata da F;

simbolo di ripetizione. Viene usato per indicare che le

operazioni in esso descritte vanno ripetute secondo le

specifiche date nella intestazione;

simbolo di operazione, Viene usato per descrivere ope­

razioni di qualsiasi natura diversa dalle precedenti;

Page 11: Fortran

IOIl

L 'operazione di assegnazione corrispondente alla locuzione «poni J! = e» èindicata con la scrittura: v+- e.

Per esemplificare come si utilizza il formalismo dei diagrammi a blocchi si ri­

porta in fig. 1.1 la descrizione, mediante questo linguaggio, dell'algoritmo 1.1,

in fig. 1.2 quella dell'algoritmo 1.2 ed in fig. 1.3 quella dell'algoritmo 1.7. Dal-

per i = 2, 3..... n

per i = 2.3 ..... n

F

simboli di connessione. Vengono usati per evidenziare

parti diverse di un algoritmo In modo da potervi fare

riferimento. Se tali parti sono descritte sullo stesso fo­

glio di carta si utilizza il primo sim bolo; in caso contra­rio il secondo.

oo

Figura 1.1. Diagramma a blocchi che de­scrive un algoritmo per il calcolo dir = min {al' a2• a3}·

Figura 1.2. Diagramma a blocchi chedescrive un algoritmo per il calcolo dir = min {a.}.

I c i c n I

Figura 1.3. Diagramma a blocchi che descrive un algoritmo per il calcolo di r = 1~i~ n{ai} ed

R= max {a.}(cfr. algoritmo 1.7).l''i<n I

Page 12: Fortran

Figura 1.5. Diagramma a blocchi che descrive il procedimento risolutivo dell'esempio 1.7.

12

l'esame di queste figure risulta evidente come il linguaggio dei diagrammi a blocchi

permetta di evidenziare il flusso di un algoritmo: mediante il simbolo di direzione

viene infatti chiaramente indicata la sequenza in cui le azioni descritte all'interno

dei singoli blocchi devono essere eseguite. Per questo motivo i diagrammi a bloc­

chi sono anche detti diagrammi di flusso.

Si osservi che utilizzando il linguaggio dei diagrammi a blocchi risultano facil­

mente individuabili alcune situazioni particolari del tipo indicato in fig. lA.

Queste situazioni che chiameremo cicli iterativi prevedono la ripetizione di una

o più istruzioni in base al verificarsi o meno della condizione specificata nel bloc­

co di decisione.

Esempio 1.7. Indicando con Xo ed h due valori reali assegnati e supponendo di

saper valutare la funzione sen x, si vuoi calcolare il valore della funzione f(x) =x sen x nei punti Xi = Xo+ ih, i ~ O, fino a che non si verifichi la condizione

f(x k ) = O per qualche k.

In fig. 1.5 è riportato il diagramma a blocchi di un procedimento che risolve

questo problema. Si osservi che il procedimento termina soltanto se è verificata

la condizione «se x sen x = O»altrimenti esso continua, dopo il blocco di deci­

sione. nella direzione indicata da F. In altre parole, se la condizione x sen x = Onon risultasse mai verificata, come ad esempio accadrebbe ponendo Xo= - l ed

h = 0.4, il procedimento non avrebbe mai fine.La presenza di un ciclo iterativo può essere allora «molto pericolosa» perchè

il diagramma di flusso che lo contiene può non rappresentare un algoritmo. Si­

tuazioni di questo tipo richiedono quindi una analisi particolare e verranno nuova­

mente discusse nel cap. lO.

A conclusione di questo paragrafo va osservato che il linguaggio dei diagrammi

F

13

v

L

F

F

Figura 1.4. Alcuni esempi di ciclo iteranvo,

a blocchi ha la seguente fondamentale proprietà: dato un qualunque problema

di natura scientifica o meno che ammetta almeno una soluzione, è possibile co­

struire un opportuno diagramma di flusso la cui esecuzione fornisce il risultato

corrispondente ad ogni possibile insieme di dati: questa affermazione, nota come

tesi di Church [2], mette in evidenza il notevole potere descrittivo del formalismo

dei diagrammi a blocchi che, come vedremo nel prossimo capitolo, è servito comemodello per il primo progetto di elaboratore elettronico che diremo elaboratore

convenzionale o alla Von Neumann [3]. D'altra parte, è importante ricordare che

il linguaggio dei diagrammi a blocchi non è l'unico modo per descrivere gli algorit­

mi. Diversi altri formalismi sono stati definiti ed utilizzati; tra questi, uno dei

più noti è quello delle funzioni ricorsive le cui caratteristiche sono servite per la

costruzione di particolari elaboratori chiamati LlSP-machines. Esistono inoltre

diversi linguaggi oggi abbastanza diffusi quali il LlSP [4], l'Algol [5), il Pascal [6]

che, pur realizzati su elaboratori convenzionali, si basano sul concetto di ricorsivi-

Page 13: Fortran

14 15

Esempio 1.9. La funzione differenza di due interi m ed n con n ~ O è definita

dalle due equazioni:tà. Pertanto, anche se il linguaggio FORTRAN oggetto di questo testo non con­

sente l'uso di costrutti ricorsivi, riteniamo opportuno concludere questo capitolo

esponendo i concetti fondamentali del formalismo ricorsivo sia per completezza

di esposizione che per l'attualità di questo argomento.(I)

(2)

diff (m, O) = m

diff(m. n) = pred (dìff Irn. pred (n))).

Esempio 1.8. Supponiamo di saper calcolare le funzioni primitive successore di

un intero n, succ(n) = n + l, e predecessore di un intero n, pred(n) = n - l.

Possiamo allora definire la funzione somma di due interi non negativi m ed n,

som (m, n), con le due seguenti equazioni:

1.3. Il linguaggio delle funzioni ricorsive ([7))

E' possibile definire in modo non formale una funzione ricorsiva tramite la

seguente definizione: una funzione si dice ricorsi va se nella sua definizione si fa

uso delle funzioni stesse. Gli esempi che seguono illustrano questo concetto. Esempio 1.10. La funzione prodotto di due interi m ed n ~ O è definita dalle

due equazioni:

Si osservi che nella (2) si è fatto uso della funzione som che supponiamo già

definita (cfr. esempio 1.8), della primitiva pred e di prod stessa.

Calcoliamo prod (3, 2):

prod (m. O) = O

prod (m, n) = som (m, prod (m, pred (n))).

Risulta evidente l'analogia tra questa definizione e quella data nell'esempio

precedente per la funzione som; le due definizioni differiscono esclusivamente per

il fatto che una usa la funzione primitiva pred e l'altra succo

(I)

(2)

som (m, O) = m

som (m, n) = su cc (som (m, pred (n»)

(I)

(2)

Tale calcolo viene detto riduzione; abbiamo infatti ridotto l'espressione som (3, 2)

ad una forma equivalente non ulteriormente riducibile, S, servendoci delle due

equazioni definitorie.

L'equazione (I) dice che la somma tra un intero m e O vale m; questa è la

parte non ricorsiva della definizione la cui presenza è sempre necessaria per assi­

curare la fine del calcolo.

L'equazione (2) dice che la somma di due interi m ed n, con n ovviamente

diverso da O, è ottenuta tramite l'applicazione della funzione successore al risul­

tato della somma fra m e pred (n). La presenza di som (m, pred (n» nel memhro

destro della (2) viene detta chiamata ricorsiva della funzione che stiamo defi­

nendo.

Così, ad esempio, il calcolo di som (3, 2) viene eseguito servendosi delle due

equazioni nel modo seguente:

Esempio 1.11. Datala lista x di elementi al' a2, .•• , an essa viene comunemente

indicata come la l, a2, ... , anI; è possibile evidenziare il primo ed i restanti ele­

menti di x usando la notazione [ali z] dove z = [a 2, a 3, ... , anI e I è l'operatore

costruttore di lista tale che [al I[a 2, a3, ... , anll = [al' a2, ... , aJ Se l'insieme

cui appartengono gli elementi della lista x è quello dei numeri reali è possibile

calcolare il minimo tra gli elementi di x mediante la funzione ricorsiva min defini­

ta dalle seguenti equazioni:

prod (3,2) = som (3, prod (3, pred (2)))

= som (3, prod (3, I)

= som (3, som (3, prod (3, pred (I)))

= som (3, som (3, prod (3, O»= som (3, som (3, O»= som (3, 3)

=6

perla(2)

calcolando pred (2)

perla(2)

calcolando pred ( I)

per la (1)

calcolando som (3,01

calcolando som (3,3)

min ([al]) = al

min ([al' a2]) = al se al < a2

min ([al' a2 ]) = a2 se al ~ a2

min ([ali z]) = min ([al' min (zj l)

(1)

(2)

(3)

(4)

perla(2)

calcolando pred (2)

per la (2)

calcolando pred ( I)

per la (1)

calcolando succ (3)

calcolando succ (4)

som (3, 2) = succ (sorn (3, pred (2»)

= succ (som (3, I»= succ (succ(som (3, pred (1)))

= succ (succ (sorn (3, O»= succ (succ (3»= succ (4)

=5

Page 14: Fortran

16

Così il minimo della lista [2, 4, 1,8) è dato da:

17

min ([2, 4, 1,8» = min ([2, min [4, 1,811)= min ([2, min ([4, min [1,8»»))

= min ([2, min ([4, mn= min ([2, l))

= l

per la (4)

perla (4)

per la (2)

per la (3)

per la (3)

min ([al' a2]) = se al < a2 allora al altrimenti a2

min ([ali z]) = min ([al' min (z l])

Alternativamente, è possibile definire la funzione min usando una sola equa­

zione:

Si osservi che se gli elementi di x sono lettere dell'alfabeto, la funzione min

permette di determinare l'elemento di x che precede tutti gli altri nell'ordina­

mento alfabetico indicato ancora con il simbolo <.

In generale, è possibile definire una funzione ricorsiva f mediante un numero

finito n di equazioni del tipo:

f(~I) = hl(~l)

f(~2) = h2(~2)

min(x) = se x = [al) allora al altrimenti

se x = [al' a2) allora se al <": allora al altrimenti a2altrimenti

se x = [ali z) allora min (Ia l , mint z j ])

altrimenti «errore».

dove con «errore» si intende la segnalazione del fatto che x non è una lista e quin­

di non appartiene al dominio di definizione della funzione min.

In questa definizione glI x) = al ed Hlf(x) è costituita da tutto quello che

segue il primo altrimenti.

Esempio J. J4. Ricordando che la funzione fattoriale di un intero n ~ O è defini­

ta come:dove ~i' i = l, 2, ... , n sono elementi del dominio di f e hi' l E;;; i E;;; n. sono com­

posizioni di funzioni primitive e/o predefinite ciascuna delle quali può essere

costruita tramite il seguente schema condizionale:n! = In! = n( n ~ I) (n - 2) . . . 2. 1

se n = O

se n> O

si deduce facilmente la seguente definizione ricorsiva:

Dagli esempi risulta evidente che l'uso di più equazioni rende più leggibile

la definizione di una funzione ricorsiva. D'altra parte. ogni funzione ricorsiva

può essere sempre definita in modo estremamente compatto mediante una sola

equazione nella quale si usano opportune condizioni per individuare la forma del

parametro e quindi la funzione da applicare. Va osservato che per descrivere fun­

zioni in forma ricorsiva non si fa uso del concetto di assegnazione.

E' possibile dimostrare che il linguaggio dei diagrammi a blocchi e quello delle

funzioni ricorsive sono equivalenti nel senso che ogni funzione è descrivibile sia

In questo schema c indica una condizione ovvero una espressione costruita

tramite funzioni e relazioni primitive o predefinite il cui risultato è un valore lo­

gico: vero oppure falso; gj è una funzione primitiva o predefinita ed H/ è una

combinazione di funzioni primitive e/o predefinite eventualmente legate dallo

schema condizionale fra le quali può figurare la funzione f.

Quanto detto viene chiarito dagli esempi seguenti dove ovunque compaia la

funzione identità id definita come id(x) = x per ogni x, conveniamo di scrivere

x in luogo di id(x) ed ancora, ovunque occorra la funzione costante k definita

da k(x) = k per ogni x, conveniamo di scrivere k in luogo dik(x).

Esempio J. J2. Scriviamo in forma generale la funzione ricorsiva som già vista

nell'esempio 1.8

som (m, n) = se n = Oallora m altrimenti succ (som (m, pred (n»)

Esempio J. J3. La funzione ricorsiva min considerata nell'esempio 1.11 può essere

definita dalle seguenti equazioni:

-

(I)

(2)

ovvero:

tattt O) = I

fatt(n) = prod(n, fatt (pre dt nj))

fatt(n) = se n = O al/ora l

altrimenti prodt n, fatt(pred(n))

Page 15: Fortran

18

con l'uno che con l'altro linguaggio [8]. La prova di questa equivalenza è data

in modo costruttivo: si può costruire una funzione che traduce ogni algoritmo

descritto in un linguaggio in un algoritmo per risolvere lo stesso problema scritto

nell'altro linguaggio. L'equivalenza può essere dimostrata anche costruendo una

funzione di interpretazione di ogni algoritmo descritto in uno dei due linguaggi.

Siccome i concetti di traduzione ed interpretazione verranno trattati anche nel

cap. 2 a proposito della realizzazione dei linguaggi simbolici di programmazione,

conviene qui precisare i due concetti da un punto di vista puramente funzio­

nale.

Siano M ed N due linguaggi; data una qualunque funzione f, siano fM ed fN le

descrizioni di f nel linguaggio M ed N rispettivamente.

Definizione l. Si dice traduttore da M ad N una funzione T tale che per ogni

funzione fMvalga la seguente proprietà:

Il traduttore deve essere quindi tale da produrre una descrizione di f nel lin­

guaggio N che rappresenti una funzione equivalente ad fM' In particolare il tra­

duttore T può essere scritto nel linguaggio M oppure N ottenendo TM o T N

rispettivamente.

Definizione 2. Un interpretatore per il linguaggio M è una funzione I tale che per

ogni funzione fM e per ogni i del dominio di definizione di f si ha

Ossia I è una funzione che applicata alla coppia (fM' i) produce il medesimo

risultato che si sarebbe ottenuto applicando direttamente fM ad i. L'interpretaioreI può essere scritto usando uno dei due linguaggi M oppure N ottenendo rispetti­

vamente 1Med IN'

L'equivalenza fra il linguaggio dei diagrammi a blocchi. B, e quello delle fun­

zioni ricorsive, R, è allora dimostrata in modo costruttivo definendo una delle

seguenti funzioni:

• il traduttore TB che associa ad un algoritmo scritto in R, fR, un algoritmo equi­

valente scritto in B, fB ;

• il traduttore T R che associa ad un algoritmo scritto in B, fB, un algoritmo equi­

valente scritto in R, fR ;

• l'interpretatore IB di algoritmi scritti in K;

• l'interpretatore IR di algoritmi scritti in B.

Notiamo che l'equivalenza tra i vari sistemi formali, in particolare tra R e B,

19

costituisce l'argomento principale che suffraga la tesi di Church già ricordata

nel paragrafo precedente; definendo infatti formalismi «abbastanza lontani»

tra loro si giunge comunque a poter descrivere la medesima classe di funzioni

che viene per questo detta classe delle funzioni calcolabili.

Page 16: Fortran

2Dal linguaggio macchina alla realizzazionedei linguaggi simbolici

2.1. Introduzione

La risoluzione di un problema presuppone la definizione di un algoritmo che,

in modo esplicito e non ambiguo, permette di ottenere dai dati iniziali il risultato.

Nella pratica, il compito di eseguire un algoritmo è affidato agli elaboratori elet­

tronici (calcolatori) ovvero a macchine costruite proprio per eseguire in modo

automatico le operazioni richieste da un algoritmo.

L'utilizzazione di un elaboratore per l'esecuzione di un algoritmo impone che

tutte le informazioni indispensabili per ottenere il risultato siano fomite alla

macchina in forma ad essa comprensibile ed in particolare devono essere oppor­

tunamente formulate le istruzioni che costituiscono l'algoritmo.

In generale diremo unità di programma la formulazione di un algoritmo in un

linguaggio comprensibile ad un elaboratore elettronico (linguaggio di program­

mazione). Quando la soluzione di un problema è determinata utilizzando quella

di opportuni sottoproblerni, l'algoritmo che permette di calcolarla è composto da

più algoritmi: quelli che risolvono i sottoproblemi e quello che, utilizzando

i precedenti, permetta la risoluzione del problema dato (cfr. esempio 1.6). Nel

seguito diremo programma l'insieme delle unità di programma che descrivono,

con un linguaggio di programmazione, gli algoritmi necessari alla risoluzione di

un problema.

Un elaboratore è fisicamente costituito da più componenti (unità hardware)

il cui funzionamento presuppone l'utilizzazione di un insieme di programmi che

vengono forniti dalla casa costruttrice e che costituiscono il software di base

dell' elaboratore.

In questo capitolo. dopo una breve descrizione delle caratteristiche hardware

comuni a tutti gli elaboratori convenzionali. sono messe in evidenza le principali

caratteristiche dei linguaggi di programmazione e sottolineate le fondamentali

differenze tra un «linguaggio macchina» ed un «linguaggio simbolico». Dopo la

descrizione delle modalità di realizzazione di un linguaggio simbolico, il capitolo

si chiude con un breve cenno alle caratteristiche essenziali del sistema operativo.

Page 17: Fortran

,...

22 23

Figura 2.1. Schema di funzionamento di un elaboratore.

Esempio 2.1. Supponiamo di lavorare con un elaboratore che riserva 8 bits per la

codifica del codice operativo e 8 bits per quella dell'indirizzo. Supponiamo inol­

tre che l'esecuzione delle operazioni aritmetiche avvenga utilizzando una parti­

colare cella dell'unità aritmetica detta accumulatore in cui si memorizza un ope­

rando prima dell'esecuzione dell'operazione e il risultato una volta che I'operazio-

Unità diuscita

Unità di controlloUnità diingresso

codice operativo indirizzo

dove codice operativo identifica l'azione che si vuole venga eseguita ed indirizzo

indica la cella su cui operare. Sia il codice operativo che l'indirizzo sono costi­

tuiti da un prefissato numero di bits. Le istruzioni del tipo ora considerato sono

dette ad Wl indirizzo.

2.3. Il linguaggio macchina

Per ogni elaboratore esiste un msierne di istruzioni che devono essere scritte

secondo regole sintattiche fissate e che l'unità di controllo sa interpretare ed

eseguire; tale insieme costituisce il linguaggio macchina. Ogni programma che

debba essere eseguito direttamente dalla macchina deve essere scritto in tale

linguaggio. In pratica ogni elaboratore ha il suo linguaggio macchina che è stretta­

mente legato alle caratteristiche dell'hardware.

D'altra parte però. per qualunque elaboratore, gli unici segni disponibili per

formare le istruzioni del linguaggio macchina sono «O» e «I ». Tenendo pre­

sente che un qualunque programma in linguaggio macchina è costituito da istru­

zioni di tipo diverso (quali ad esempio quelle aritmetiche. di assegnazione. di in­

gresso/uscita e di controllo) ciascuna di esse deve essere opportunamente codi­

ficata per distinguerla da tutte le altre. In generale pgni istruzione è codificata

su un ugual numero di bits,

Le istruzioni hanno una struttura sin tattica molto elementare quale ad esem­

pio la seguente:

2.2. Unità hardware di un elaboratore convenzionale

Le componenti hardware fondamentali per un qualsiasi sistema di calcolo

sono le seguenti:

• unità di ingresso che è un organo che permette di ricevere dall'esterno i dati

iniziali e la sequenza delle istruzioni;

• unità di memoria che è un organo capace di conservare informazioni e di for­

nirne, su richiesta. una copia;

• unità di controllo che è un organo che permette di interpretare e far eseguire

la sequenza delle istruzioni;

• unità aritmetica che è un organo che permette di eseguire operazioni sia arit­

metiche che logiche;

• unità di uscita che è un organo che permette di comunicare all'esterno i ri­

sultati.

Le componenti hardware più comunemente usate come supporti per le unità

di ingresso e di uscita sono videoterminali, stampanti, nastri magnetici, dischi,

dischetti (floppy disks); alcune delle quali possono essere usate anche per la me­

morizzazione delle informazioni e quindi possono essere viste come estensioni

delle unità di memoria imemoria di massa o ausiliarie). _La memoria è fisicamente costituita da un insieme di elementi, ciascuno dei

quali può assumere due soli stati fisici rappresentabili dai simboli «O» ed «I».

Dalle caratteristiche fisiche degli elementi che costituiscono l'unità di memoria,

segue che le informazioni elaborabili da un calcolatore devono essere rappresenta­

te con una sequenza finita di cifre binarie ciascuna delle quali viene chiamata

bit (hinary digir). Per tutte le applicazioni pratiche il bit è una unità troppo pic­

cola di informazione e per questo si considera spesso come unità di informazione

il byte che corrisponde ad un raggruppamento di 8 bits. Un byte è per esempio

sufficiente a codificare i caratteri dell'alfabeto (cfr. cap. 12).

Per rappresentare quantità numeriche si considerano come unità di informa­

zione raggruppamenti di un numero fissato di bits. Tali raggruppamenti. ciascuno

dei quali contiene un'unica informazione. prendono il nome di unità di memorianumeriche e la loro lunghezza può variare da elaboratore ad elaboratore. Nel segui­

to il termine locazione o cella verrà usato per indicare un raggruppamento di unità

di informazione (numeriche o meno) a cui è associato un numero detto indirizzo.L'indirizzo permette di individuare la posizione di una cella nella memoria secon­

do modalità strettamente dipendenti dalle caratteristiche dell'elaboratore usato.

In fig. 2.1 è schematizzato il funzionamento di un elaboratore; le frecce a tratto

continuo denotano una trasmissione di informazioni e quelle tratteggiate l'azione

di controllo.

Page 18: Fortran

24 25

ne sia stata eseguita. Sia 000000 IO il codice operativo per l'operazione di cari­

camento ovvero per l'assegnazione del valore contenuto in una cella all'accumula­

tore; sia 000000 Il il codice operativo per l'operazione di memorizzazione ossia

per l'assegnazione del contenuto dell'accumulatore ad una assegnata cella; sia

inoltre 00000001 il codice operativo per l'operazione di addizione. Consideriamo

le seguenti istruzioni

soprattutto poco leggibili. Essi inoltre non sono porta bili, ovvero non sono tra­

sferibili da un elaboratore ad un altro che abbia caratteristiche costruttive diverse.Si osservi infine che la scrittura di un programma in linguaggio macchina richiedela conoscenza degli indirizzi dei dati e delle istruzioni per potervi far riferimento

all'interno delle istruzioni stesse.

0000001000001000

0000000100001001

0000001100001010

Tenendo presente il significato dei codici operativi, l'effetto dell'esecuzionesequenziale di queste istruzioni è il seguente: con la prima istruzione si carica nel­

l'accumulatore il contenuto della cella di indirizzo 00001000, con la secondaistruzione si somma al contenuto dell'accumulatore quello della cella di indi­rizzo 00001001, infine con la terza istruzione si memorizza il contenuto dell'ac­

cumulatore nella cella di indirizzo 0000 lOl O. Supponendo che nelle celle di in­dirizzi 00001000 e 00001001 siano rappresentati i numeri 2 e 3 rispettivamente,l'esecuzione delle istruzioni precedenti implica le trasformazioni descritte in

fig. 2.2 dove r(i) indica la rappresentazione in memoria del numero i.

2.4. I linguaggi simbolici

Le difficoltà legate all'uso del linguaggio macchina sono superate con l'intro­

duzione dei linguaggi simbolici di programmazione. Ci occuperemo in questo pa­

ragrafo della struttura e dei principi fondamentali dei linguaggi simbolici che si

basano sul linguaggio dei diagrammi a blocchi. Non verranno invece trattati altri

esempi di linguaggi simbolici, quali ad esempio quelli basati sullo schema delle

funzioni ricorsive; tali linguaggi si dicono linguaggi funzionali e sono profonda­

mente diversi dai precedenti.In un linguaggio simbolico i codici operativi sono sigle mnemoniche quali ad

esempio LOAD, ADD, STO, e i riferimenti alle celle di memoria dell'elaboratore

non sono più i loro indirizzi effettivi ma nomi simbolici chiamati anche etichette.

In generale i prograrnrru 1I1 uuguaggio macchina risultano molto lunghi e

Figura 2.2. Calcolo di 2 + 3 mediante le istruzioni dell'esempio 2.1.

hanno lo stesso effetto delle istruzioni del linguaggio macchina usate nell'esempio2.1.

A

PESOXYl

LOADADDSTO

I linguaggi simbolici si dividono in due grandi gruppi: quelli assemblativi (o ditipo assem bly) le cui istruzioni sono in corrispondenza biunivoca con quelle del

linguaggio macchina, e quelli compilativi ed interpretativi per i quali tale corri­

spondenza non è prevista e che sono progettati con lo scopo di facilitare la stesura

dei programmi. Ovviamente, per eseguire un programma scritto in un linguaggio

simbolico, occorre che esso sia «tradotto» nel linguaggio macchina o «diretta­mente interpretato».

Si chiama traduttore di un linguaggio L per un elaboratore M un programmache, ricevenuo in ingresso un qualsiasi programma sintatticamente corretto scritto

Esempio 2.2. Siano LOAp, ADD eS'I'O i codici operativi che un linguaggio sim­

bolico utilizza per indicare rispettivamente le operazioni di caricamento, aòdi~t'?~

ne- e mernorizzazione. Se supponiamo di associare i nomi simbolici A, PESO,XY l alle celle che nell'esempio 2.1 sono identificate dagli indirizzi 0000 l 000,

0000 l 00 l, 0000 lO lO, le seguenti istruzioni sim boliche

Accumulatore

r(5)

00001010

r(3 )

r(3)

r(3)

r(3)

00001001

r(2)

r(2)

r(2)

r(2)

00001000

Dopo la 3a

istruzione

Dopo la 2a

istruzione

Dopo la l aistruzione

Stato iniziale

Page 19: Fortran

26 27

nel linguaggio L (programma sorgente) è in grado di produrre in uscita il pro­

gramma equivalente scritto nel linguaggio macchina di M (programma oggetto).

I La traduzione avviene generalmente in due fasi: la prima è nota come costruzione: della tavola dei simboli e l'altra come produzione del programma oggetto.

Nella tavola dei simboli ad ogni nome simbolico incontrato durante la scansione

del programma viene associato l'indirizzo relativo della cella da essa individuata

ovvero la sua posizione riferita alla cella di indirizzo zero dove si pensa sia memo­

rizzata la traduzione della prima istruzione del programma. In generale la tavola dei

simboli contiene anche altre informazioni riguardanti il contenuto della cella.

Nella fase di produzione del programma oggetto vengono sostituiti ai codici

operativi mnemonici i corrispondenti codici binari e, grazie alla tavola dei sim­

boli, ai nomi simbolici vengono sostituiti gli indirizzi relativi loro associati.

In caso di errori sin tattici nel programma sorgente, il traduttore generalmente

non crea il programma oggetto ma fornisce un elenco di tali errori e la loro posi­

zione nel programma; questa eventualità è nota come produzione del diagnostico.I programmi traduttori relativi a linguaggi di tipo assembly si dicono assembla­

!2r:.imentre quelli relativi a linguaggi di tipo compilativo si dicono compilatori.La traduzione di un programma scritto in un linguaggio compilativo può avve­

nire. per esempio, secondo lo schema riportato in fig. 2.3 nella quale il compi­

latore è realizzato mediante la coppia traduttore-assem blatore. In questo caso il

traduttore permette di passare dal programma sorgente ad un programma equi­

valente scritto nel linguaggio assembly dell'elaboratore usato e l'assemblatore

fornisce successivamente il programma oggetto scritto in linguaggio macchina.

D'altra parte è opportuno ricordare che esistono compilatori che non prevedono

l'uso di un assemblatore ed eseguono una traduzione diretta in linguaggio mac­

china.

LOOP LOAD B

ADD A

456

Indirizzo

relativo

ABA

BIC

C

LOAD ABA

ADD BIC

STO C

STOP

ABA DC 7

BIC DC 8C DC *

END

Nome

simbolico

sono costituite da un'etichetta seguita da un codice operativo simbolico e da

un'altra etichetta che indica la cella di memoria interessata dall'operazione o un

valore quale ad esempio una costante numerica. La prima e la seconda etichetta

possono eventualmente mancare.

Così, ad esempio, nelle istruzioni

LOAD ed ADD sono codici operativi mentre LOOP. A e B sono etichette. Con­

sideriamo il seguente programma:

dove i codici operativi LOAD, ADD, STO sono quelli definiti nell'esempio 2.2,

mentre il codice operativo DC indica l'operazione di definizione di costante, che

consiste nel memorizzare nella cella di memoria individuata dalla etichetta che

compare alla sinistra del codice DC il valore specificato alla sua destra: se tale valo­

re è * !'istruzione non modifica il contenuto preesistente nella cella stessa. Suppo­

nendo che la traduzione di ogni istruzione sia contenuta in una cella e che durante

la costruzione della tavola dei sim boli si associ un indirizzo relativo ad ogni eti­

chetta incontrata alla sinistra di ogni codice operativo. la tavola dei sim boli ri­

sulta la seguente:Programma

assemblyTraduttore

Assemblatore

I \

i;

Figura 2.3. Un possibile schema di compilazione.

AI nne di illustrare brevemente il funzionamento di un asse m blatore conside­

riamo il seguente esempio.

Se i codici operativi LOAD. ADD e STO hanno la codifica binaria considerat a

nell'esempio 2.1 e se il codice della istruzione STOP è 00000000. il programma

oggetto è il seguente:

Esempio 2.3. Supponiamo di utilizzare un linguaggio assemblativo le cui istruzioni

Page 20: Fortran

Si osservi che i numeri binari 100, 101, 110, 111, 1000 sono i corrispondenti

delle costanti decimali 4, 5, 6, 7, 8. L'istruzione END ha lo scopo di indicare

la fine fisica del programma e pertanto non viene tradotta.

2.5. La realizzazione di un linguaggio simbolico

Con il termine realizzazione di un linguaggio simbolico si vuoi tradurre il ter­

mine inglese implementation con il quale si intendono le modalità che vengono

seguite per arrivare all'esecuzione di un programma scritto In quel linguaggio.

Due possibili schemi di realizzazione sono quello basato sulla traduzione e quello

basato sulla interpretazione.

28

Indirizzo

ol

2345

6

contenuto

0000001000000100

0000000100000101

0000001100000110

0000000000000000

0000000000000111

0000000000001000

non definito

29

Compilatoreo assemblatore

Linker

Dati

Realizzazione mediante traduzione

Ricordiamo che un programma sorgente può essere costituito da una o più

unità di programma. Nella realizzazione di un linguaggio simbolico mediante

traduzione ogni unità di programma viene separatamente tradotta in una oppor­

tuna successione di istruzioni del linguaggio macchina (modulo oggetto) cui è

associa ta la sua tavola dei sim boli.Il programma oggetto risulta quindi costituito dall'insieme dei moduli oggetto.

Per rendere eseguibile il programma sarà necessario sostituire agli indirizzi relati­

vi presenti in ciascuna tavola dei simboli gli indirizzi assoluti ovvero quelli deter­

minati in base all'indirizzo effettivo della cella a partire dalla quale il programma

verrà memorizzato. Tale compito viene assolto da un opportuno programma

(/inker) che, oltre a determinare gli indirizzi assoluti, crea i necessari collegamenti

tra i diversi moduli oggetto e produce la versione eseguibile del programma tpro­

gramma eseguibile). A questo punto può avere inizio la fase di esecuzione, durante

la quale avviene la lettura degli eventuali dati. In fig. 2.4 si riassume il procedi­

mento ora descritto.Si osservi che un programma può essere affetto da errori di varia natura:

• errori che vengono segnalati dal diagnostico nella fase di traduzione (errori

sin tattici)

Figura 2.4. Realizzazione di un linguaggio simbolico mediante traduzione.

• errori che vengono segnalati dal linker (per esempio quando venga fatto ri­

ferimento ad una unità di programma che non è disponibile);

• errori che vengono segnalati in fase di esecuzione (per esempio si cerca di ese­

guire una operazione matematicamente non definita quale a/b con b = O). Questo

tipo di errore è il più difficile ad essere corretto, in quanto sia la sua segnalazione

che la sua individuazione nel programma sorgente dipendono dal software del­

l'elaboratore usato;

• errori che non possono essere segnalati (errori logici). In questo caso il pro­

gramma sorgente non descrive la soluzione della classe di problemi proposta.

L'assenza di errori di questo tipo può essere in parte garantita tramite la verifica

dei risultati ottenuti per problemi di cui è nota la soluzione.

Realizzazione mediante interpretazione

Un'altra modalità di realizzazione di un linguaggio è quella che utilizza un

~rogramma detto interpretatore, talvolta già realizzato in hardware, come per il

linguaggio BASIC nei personal computers. Un interpretatore è in grado di leggere,

Page 21: Fortran

3130

, ~.-..-------------------aq;---_....._-----------

Figura 2.5. Procedimento di interpretazione.

2.6. Il sistema operativo

Le interazioni tra l'utente ed il sistema di calcolo avvengono di solito attraver­

so un'interfaccia di tipo software chiamata sistema operativo che consiste nel­

l'insieme di quelle procedure che controllano tutte le risorse di tipo hardware

e/o software di una installazione. In ultima analisi un sistema operativo è un in­

sieme di programmi tramite i quali si tende ad ottimizzare il tempo di utilizzo

dell'elaboratore e a rendere tale utilizzazione «amichevole» per l'utente.

L'evoluzione dei sistemi operativi è profondamente legata all'evoluzione della

tecnologia degli elaboratori da una parte e alle esigenze degli utenti dall'altra. So­

no stati così messi a punto sistemi operativi che seguono filosofie diverse e per­

mettono gestioni diverse delle risorse di un sistema di calcolo. Ad esempio i si-

stemi basati sul principio della monoprogrammazione consentono l'elaborazione

sequenziale di più programmi costituenti una sequenza di lavori usualmente me­

morizzata su una unità a disco magnetico. Tali sistemi vengono detti di solito

«Disk operating systerns» (DOS). A differenza dei precedenti i sistemi che usa­

no la tecnica della spartizione del tempo (time-sharingv dedicano ciclicamente

tutte le risorse del sistema ad un lavoro per un periodo di tempo prefissato, con­

sentendo un'elaborazione pseudo-parallela dei lavori proposti da più utenti.

Un altro tipo di sistema operativo è quello basato sul principio della multipro­

grammazione che prevede la presenza di più programmi nell'unità di memoria ed

elahora un programma finchè esso non richiede un'operazione di ingresso/uscita.

Il tempo necessario allo svolgimento di questa operazione. che generalmente è

molto maggiore di quello necessario per eseguire altri tipi di operazioni. viene di

solito sfruttato per iniziare o proseguire l'esecuzione di qualche altro programma

presente in memoria.

I sistemi operativi svolgono le loro operazioni su richiesta degli utenti grazie

ad un programma. il supervisore, che fa parte del sistema operativo stesso. Il su­

pervisore è in grado di interpretare un dato insieme di comandi che è caratteristi­

co di ogni singolo sistema operativo; ad esempio, per attivare le diverse fasi del­

l'elaborazione di un programma quali la compilazione. l'attivazione del linker e

l'esecuzione si devono dare opportuni comandi al supervisore: analogamente

devono essere esplicitamente specificati i comandi che permettono di eseguire

operazioni di correzione, mernorizzazione o cancellazione di programmi e di dati.

I sistemi che prevedono la multiprograrnmazione e/o il tirn e-sharing sono in­

stallati su elaboratori che devono soddisfare contemporaneamente più utenti.

Oggi la tecnologia elettronica ha consentito la «personalizzazione» del calcolo,

mettendo a disposizione personal com puters a prezzi accessibili anche a singoli

utenti. di fatto rendendo meno sentita l'esigenza di sofisticati sistemi operativi

nel senso sopra accennato. Anche in un personal computer però. la comunicazione

uomo-macchina avviene tramite il sistema operativo (usualmente di tipo DOS).

Pertanto, qualunque sia il sistema di elaborazione usato. l'utente dovrà aver ac­

quisito una certa padronanza del linguaggio di comandi del corrispondente siste­

ma operativo.

RisultatiIn terpretatore

Programmasorgente

tradurre ed eseguire, ossia interpretare ciascuna istruzione del programma sor­

gente insieme ai dati. In questo caso lo schema realizzativo diventa quello ripor­

tato in fig. 2.5.

Il grande vantaggio dell'interpretazione rispetto alla traduzione risiede nel fatto

che gli errori sono segnalati nel momento in cui si verificano con la precisa ed

immediata indicazione dell'istruzione del programma sorgente che li ha provo­

cati. Il procedimento dell'interpretazione risulta quindi utilissimo in fase di messa

a punto di un programma in cui è fondamentale un diagnostico più ricco possi­

bile.

Ci sono però alcuni svantaggi nell'uso dell'interpretazione rispetto alla tradu­

zione. tra i quali più evidente è la maggior lentezza complessiva della elahorazione

(si pensi al caso di un procedimento ripetitivo in cui, ad ogni ripetizione, ciascuna

istruzione deve essere letta, tradotta ed eseguita).

In pratica alcuni nnguaggi sono usualmente realizzati tramite compilazione

(esempi sono il FORTRAN, il COBOL, il PLI) mentre altri, quali il BASIC, l'APL,

il LISP sono di solito realizzati mediante interpretazione.

Page 22: Fortran

3Rappresentazione dei numeri

3.1. Numeri interi

II sistema di numerazione a noi più familiare è quello decimale nel quale il

numero IO (dieci) è la base ed i numeri interi O, l, 2...., 9 costituiscono le cifre.

Altri sistemi di numerazione che interessano le applicazioni sono quello binario

che opera con la base 2 (due) e le cui cifre sono costituite dai simboli O e l;

quello ottale che utilizza la base 8 (otto) e le cifre O, 1,2,3,4, 5,6,7; quello

esadecimale che, usando come base il numero 16 (sedici), utilizza come cifre i

simboli O, 1,2,3.4,5,6,7,8,9, A, B, C, D, E, F.

Nel seguito il simbolo N indicherà un numero in base lO mentre (N)~ indicherà

che il numero intero N è rappresentato nella base {3. Se N < <Xl, si ha che

(3.1 )rn

(N)il == ± L ~{3k,k=O

01<00

dove aj , j == O, l, ... ,01 sono cifre del sistema di numerazione in base Il.

Fissato Il, il massimo numero NOlax

rappresenta bile mediante m < 00 cifre è

11m - l.

Conversione in base dieci

Supponendo nota la rappresentazione di N in base Il è possibile trovare la rap-

NOlax

== 9999 == 104 - I

NOlax == ( III 1)2 == 24- Im==41l==2

Esempio 3.1. 1471 == I x 103 + 4 x 102 + 7 x 101 + I x 100

(1471)8 == l x 83 + 4 x 82 + 7 x 8 1 + I x 8°

(1471 )1& == l x 163 + 4 x 162 + 7 x 16 1 + l x 16°

Esempio 3.2. m == 4 Il == lO

Jnz .

Page 23: Fortran

34 35

presentazione in base dieci applicando direttamente la (3.1) dove, per comodità

di notazione, le cifre ak e la base {3 vengono espresse in base dieci.

Esempio 3.3. (3471)8 = 3)( 8 3 + 4)( 82 + 7)( 81 + I )( 80 = 1849

(3471)16=3)( 163+4)( 162+7)( 161+ 1)( 160=5845

(AI)16 = 10)( 16' + l )( 160 = 161

( 10)2 = I )( 2' + O )( 20 = 2

(100)2 = l )( 22 + O )( 2' + O )( 20 = 4

(1111)2 = l )( 23 + 1)( 22 + l )( 21 + I )( 20 = 15.

dell'algoritmo descritto sopra dà luogo ai seguenti passi:

i = O No = 37 è dispari ao = I

i= I N = 18 è pari a, = OI

i = 2 N2 = 9 è dispari a2 = I

i = 3 N3 = 4 è pari a3 = O

i = 4 N4 = 2 è pari => a4 = O

i = 5 N = I è dispari => a5 = l5

quindi la rappresentazione binaria del numero 37 è datta dalla successione

Una volta determinate ao ed a" le restanti cifre binarie ak, k = 2, ... , r saran­

no ottenute in modo analogo. Si perviene così al seguente algoritmo:

Conversione in binario

Assegnato un intero N in base dieci è possibile ottenere la sua rappresentazio­

ne in base (3; in particolare, l'equivalente binario del numero N può essere otte­

nuto dalla (3.1) tenendo presente che la cifra ao di un numero binario è zero

se e soltanto se il numero è pari. Allora, indicato con r un intero positivo tale

che 2r.,;;; N < 2r + " si ha:

se m = 32 O~ N .,;;; 231 - I = 2 147483647.

Nm ax

= (OIII ... 1)2 = 2(m - 1) - l;

pertanto è possibile rappresentare con m bits tutti e soli i numeri interi positivi

N tali che O.,;;; N ~ Nmax . In particolare per m = 16 ed m = 32 si hanno le limi­tazioni seguenti:

Supponendo 2r.,;;; N < 2r + " sia m> r un numero finito e prefissato di cifre

binarie destinate alla rappresentazione di N; evidentemente, tenendo presente la

(3.1), dovrà essere ak = O, (r + l) .,;;; k ~ (m - I). Così per esempio se m = 7 la

rappresentazione binaria di 37 è data da (0100101)2 mentre, fissato m = IO,

si ha (0000100101)2'

Va inoltre osservato che nella rappresentazione di un intero in un elaboratore

vengono usati un numero finito m di bits il primo dei quali indica il segno: tutti

i numeri positivi sono caratterizzati da una rappresentazioni binaria con il primo

bit uguale a zero. Così ad esempio il numero 109 = (110 11O1)2 verrà memoriz­

zato, supponendo m = io, come 000 Il OIl OI dove il primo bit (O) indica il

segno (positivo) e le restanti nove cifre contengono la rappresentazione binaria

di 109.

Da quanto detto segue che il massimo numero intero positivo rappresentabile

con m bits di cui il primo riservato al segno è rappresentato dalla cifra O seguitada (m - I) cifre I ovvero

r r

dove No = N = L ak2k = ao + L ak 2k ;k=O k=1

/ I se No è dispari

ao="<,O se No è pari

/ I se N, è dispari

al =""-O se N, è pari

Algoritmo 31.

I. Leggi: N, r

2. poni No = N3. ripeti per i = O, l, ... , r - I

3.1. se N j è dispari allora: poni ai = I ed esegui 3.2

altrimenti: poni ai = O ed esegui 3.2

3.2. poni N j + , = (N j - a j)/2

4. poni ar

= Nr

5. stop.

Esempio 3.4. Vogliamo trovare la rappresentazione binaria di N = 37. Dalla re­

lazione 25 ,ç 37 < 26 segue che si devono calcolare 6 cifre binarie. L'applicazioneIl termine overflow indica il tentativo di rappresentare in un elaboratore numeriN>N .max

\~

Page 24: Fortran

36

Interi negativi

SI è detto che ogni numero binario positivo è caratterizzato dalla presenza della

cifra O in prima posizione; essendo stato scelto il primo bit a significare il segno,:,ç questo è uguale ad I il numero binario è inteso essere negativo. La presenza del­

la cifra l in prima posizione è ottenuta rappresentando i numeri negativi sotto

forma di complemento a due. Si ricordi che si dice complemento a due di un

numero binario rappresentato con m bits la differenza fra quella potenza di 2

che è rappresentata dalla cifra l seguita da m cifre O ed il numero stesso.

Esempio 3.5. Se m = 4 la rappresentazione del numero 5 è O101. Per ottenere

la rappresentazione di - 5 si deve calcolare la differenza (10000)2 - (OlO1)2

che è uguale a (1111)2 - (0101)2 + (0001)2 essendo (10000)2 = (1111)2 +

+ (0001)2' Si osservi che la sottrazione (1111)2 - (0101)2 è facilmente realiz­zata invertendo logicamente le cifre del sottraendo, ossia sostituendo alla cifra

O una cifra I e viceversa. Si ha allora (10000)2 - (0101)2 = (0101)2 - (0001)2 =

= (1011)2' Il numero (1011)2 è dunque la rappresentazione di - 5 su m = 4 bits.

In pratica, dato un numero binario positivo, ossia con un bit O in prima posi­zione, si ottiene la rappresentazione del suo opposto invertendo logicamente

le m cifre e quindi sommando 1 al risultato dell'inversione logica. Tutte queste

operazioni su un elaboratore sono facilmente realizzate in hardware.La rappresentazione dei numeri negativi nella forma di complemento a due

consente di unificare le operazioni di addizione e sottrazione e quindi di sempli­

ficare l'hardware dell'elaboratore; la rappresentazione della differenza tra due

numeri è infatti uguale alla rappresentazione della somma tra il primo ed il com­

plemento a due del secondo.

Esempio 3.6. Sia m = 4; calcoliamo 5 - 2. Questa operazione si può effettuare in

binario come segue:

(OlO1)2 + (10000)2 - (0010)2 - (10000)2 = (Ol O1)2 + (1110)2 - (10000)2 =

= (10011)2 - (1000U)2 = (0011)2 = + 3.

37

(0010)2 + (10000)2 - (0101)2 - (10000)2 = (0010)2 + (1011)2 - (10000)2 =

= (1101)2 - (10000)2 = (- 0011)2'

Anche in questo caso la sottrazione finale (110 1)2 - (10000)2 non viene ese­guita: (1101)2 è già il risultato finale in quanto rappresenta il complemento adue di 3 ossia - 3.

I numeri interi negativi N rappresentabili con m < 00 bits nella forma di com­plemento a due sono tutti e soli quelli per cui - 2(m- 1) ~ N < O. Per m = 16

si ha N ~ - 215 = - 32768 mentre per m = 32 vale la limitazione N ~ - 231 == - 2147483648.

3.2. Numeri reali

Fissata una base di numerazione (3 è possibile rappresentare un qualsiasi numeroreale x finito e diverso da zero nella forma:

(3.2)

dove ai' ~ i ~ m sono cifre del sistema di numerazione usato e b è un interoespresso nella base (3. La rappresentazione (3.2) del numero x è detta in virgola

mobile normalizzata (floating point); le cifre al' a2, ... , am costituiscono lamantissa mentre l'intero b è detto caratteristica.

Esempio 3.8. I numeri decimali

-0.1471 +37.1 -0.0125 +0.003 +300

sono rispettivamente rappresentati in virgola mobile normalizzata come:

-0.147110° +0.371102 -0.12510- 1 +0.310- 2 +0.3103 .

Da quanto detto segue che, indicata con (X)(3 la rappresentazione di un qual­siasi numero reale x diverso da zero in base (3, si ha:

Conversione in binario

Per determinare la rappresentazione binaria di un numero reale x espresso inbase dieci si consideri dapprima il problema di determinare le cifre binarie dellamantissa di un numero decimale x, O < x < l. Dalla relazione:

Si osservi che l'ultima sottrazione di fatto non viene eseguita nella macchina.

Infatti, siccome il numero di bits (m = 4) fissati per la rappresentazione degli

interi è insufficiente a rappresentare il risultato dell' operazione (O101)2 + (1110)2

= (100 Il )2' basterà eliminare il primo bit di tale risultato per tener conto anchedella successiva sottrazione ed ottenere il risultato finale (0011)2'

Esempio 3.7. Sia ancora m = 4; vogliamo calcolare 2 - 5. Si ha:

(3.3)m

(X)(3=±0.a1a2... am(3 b = [aj

(3 i.(3b.j= l

Page 25: Fortran

38 39

3.3. Rappresentazione finita ed errori di arrotondamento

Nella pratica le caratteristiche hardware di un elaboratore impongono precise

limitazioni sul numero di cifre utilizzate per la rappresentazione di un numero

e. pertanto, solo un sottoinsieme dei numeri reali può essere rappresentato su un

determinato sistema di calcolo. Più precisamente. indicata con (1 la base di nume­

razione usata dall'elaboratore, sia m < 00 il numero di cifre utilizzato per la rnan­tìssa. n < 00 quello per la caratteristica e siano L ed U rispettivamente il massimo

ed il minimo intero rappresentabile con le n cifre della caratteristica. Se F è l'in­

sieme dei numeri reali rappresentabili suU'elaboratore, F è costituito da tutti e

soli i numeri reali x la cui rappresentazione in virgola mobile normalizzata ha una

caratteristica b tale che L ~ b ~ U ed una mantissa costituita al più da m cifre

diverse da zero. Sono pertanto elementi di F sia il numero zero, la cui rappre­

sentazione è caratterizzata da ai = O, l ~ i ~ m, che tutti i numeri reali rappre­

sentabili nella forma

(3.4) ± O. al a2 · .. am O... O ... (1b, al "* O. L ~ b ~ U.

I valori delle costanti (1, m, L ed U sono dati forniti dalle case costruttrici in

quanto strettamente legati alle caratteristiche hardware dell'elaboratore. La base

di numerazione (1 è generalmente due ma è spesso usato anche il sistema di

numerazione ottale o esadecimale. Le costanti L ed U delimitano l'ordine di

grandezza dei dati rappresentabili su un elaboratore: il tentativo di rappresentare

numeri la cui caratteristica è maggiore di U è detto overflow mentre quello di

rappresentare numeri con caratteristica minore di L è detto underflow. Il signi­

ficato del numero m di cifre destinate alla mantissa è strettamente legato alla

«precisione» con cui l'elaboratore lavora. Sia infatti x un numero reale la cui

rappresentazione nel sistema di numerazione usato dall'elaboratore è data da:

(3.5) ± O. al a2 · .. am am + l' .. am + i e», ai "* O, L ~ b ~ U

dove am + i "* O per qualche i > O.Siccome la rappresentazione (3.5) ha una mantissa con cifre diverse da zero

nelle posizioni che seguono la m-esima, il numero x non appartiene ad F e non

può essere rappresentato sull'elaboratore; esso è allora sostituito da una sua ap­

prossimazione che indicheremo con fl(x) appartenente ad F. Il valore fl(x) è ot­

tenuto da (3.5) per troncamento oppure per arrotondamento; nel primo caso

fl(x) è dato da:

(3.6) fl(x) = ± O.al a2... a

m(1b

nel secondo:

Il1\

segue:

m

2x = al + [ ai 2- (i-l}

i= 2

da cui, posto CI = 2x, si ha: al = l se Cl ~ l, al = O se Cl < l. Analogamente,

posto c2 = 2( CI - al', si ha a2 = l se c2~ l, a2 = O se c2< l. In generale, posto

Ci = 2(c i _ 1- ai_ l)' la i-esima cifra ai della mantissa é data da:

a. =/' l se Ci~ l

I """O se Ci< 1.

Esempio 3.9. Si vuoI determinare la rappresentazione binaria del numero deci­

male x == + 0.1. Applicando il procedimento sopra indicato si ottiene:

(+ 0.00011001100110011 .... ')2

ovvero il numero decimale 0.1 non ha una rappresentazione binaria finita in quan­

to esso è, in base due, un numero periodico di periodo 00 Il. Si osservi inoltre

che la rappresentazione binaria in virgola mobile normalizzata del numero deci­

male x == 0.1 è data da

+ 0.1100110011001100 ... (1101, (1 = (10)2 = 2

essendo 101 la rappresentazione binaria di - 3.

Sia ora x un qualunque numero reale espresso in base dieci. La sua rappre­

sentazione binaria è ottenuta convertendo sia la parte intera che quella decimale;

la conversione della parte intera avviene seguendo le regole viste nel paragrafo

precedente mentre quella della parte decimale avviene applicando il procedi­

mento di conversione ora descritto.

Esempio 3.10. Tenendo presenti i risultati degli esempi 3.4 e 3.9 si ha che la rap­

presentazione binaria del numero decimale + 37.1 è data da

(+ 100\01.000\100110011001\ .. ')2

La rappresentazione binaria in virgola mobile normalizzata di 37.1 è allora:

+ 0.\00\01000\\00\\00\\ ... fflilo. (1 == (10)2 == 2

essendo 0\\ O la rappresentazione binaria di + 6.

(3.7)se am + 1<(1/2

se am + I ~ (1/2

Page 26: Fortran

40 41

mentre, se tl(x) è ottenuto da (3.7), valgono le seguenti relazioni:

caratterizzati da valori diversi della costante m: il sistema in precisione semplicee quello in doppia precisione. La denominazione scelta per i due sistemi è legata

al fatto che il numero di bits destinati a rappresentare il numero nel secondo si­

stema è il doppio di quello usato nel primo e il passaggio deIIa precisione semplice

a quella doppia implica un aumento della precisione nel senso che, daIIa preci­

sione di macchina f m caratteristica della precisione semplice, si passa ad una pre­

cisione di macchina minore o uguale di f~. Si osservi che, contrariamente a quan­

to avviene per la mantissa, il numero di cifre usate come caratteristica è general­

mente lo stesso sia nella semplice che nella doppia precisione.

Quanto detto in questo paragrafo mette in evidenza che in un elaboratore la

rappresentazione di quantità reali non intere non è in generale esatta: essa coin­

cide con il valore esatto a meno di una quantità finita, diversa da zero che di­

pende dalla precisione di macchina.

Sull'insieme F dei numeri rappresentabili su un elaboratore sono definite le

operazioni elementari di addizione, sottrazione, moltiplicazione e divisione.

Indicata con . una qualunque operazione elementare, sia 8 la corrispondente

operazione definita in F. Il modo con cui 8 viene effettivamente eseguita dipende

dall'elaboratore usato e, in generale, si ha:

x 8 y = tl(x . y) = (x . y) (1 + f), Ie I~ f m

per ogni coppia di valori x ed y appartenenti ad F. La differenza tra x . y e

x 8 y rappresenta l'errore di arrotondamento commesso nell'esecuzione dell'o­

perazione e dipende daIIa precisione con cui si opera. Le operazioni di somma e

moltiplicazione definita su F sono generalmente commutative ma non associative

e anche la proprietà distributiva non è più valida quando si usa una aritmeticafinita ovvero quando le operazioni vengono eseguite usando una precisionefinita.

eR = (x - tl( x»/x.

tl(x) = x(l + f),

Si osservi che le limitazioni ottenute per gli errori di arrotondamento dipendo­

no dal metodo usato per calcolare flf x): il troncamento può portare ad errori

che possono essere il doppio di quelli che sarebbero stati ottenuti con l'arroton­

damento. Va inoltre sottolineato che gli errori relativi, al contrario di quelli

assoluti, non dipendono dalla caratteristica ovvero non dipendono dall'ordine

di grandezza del numero x.Da quanto detto segue che il valore tl(x) ottenuto da (3.5) per troncamento

o per arrotondamento, è tale che

è facilmente verificabile che, quando tl(x) è ottenuto per troncamento da (3.6),

si ha:

eA

= x - tl(x)

ed errore relativo di arrotondamento la quantità

In ogni caso, se x ha una rappresentazione di tipo (3.5) la sostituzione di x con

tl(x) dà luogo ad un errore, detto errore di arrotondamento, il cui valore dipende

dalla tecnica usata per determinare tl(x). In particolare, detta errore assoluto di

arrotondamento la quantità

Vogliamo eseguire queste stesse operazioni utilizzando, nel sistema decimale,

una rappresentazione in virgola mobile normalizzata con m = 4 cifre di mantissasupponendo che tl(x) sia ottenuto per troncamento dal valore di x. In questaipotesi si ha:

(x l Ef) x2 ) mx3

= (0.2000 10° I±J 0.2500 10- 3) Ef) 0.7800 10- 3 =

= (0.2000 10° Ef) 0.0002 100)Ef) 0.7800 10~ 3 =

= 0.2002 10° I±J 0.0007 10° = 0.2009 10°

dove fm

è data da

se tl(x) è calcolato per troncamento

se tl(x) è calcolato per arrotondamento

La quantità fm

è detta precisione di macchina e rappresenta una limitazione

superiore per l'errore relativo di arrotondamento quando al valore x, non esat­

tamente rappresentabile sull'elaboratore, si sostituisce la sua approssimazione

tl(x). La precisione di macchina è una quantità caratteristica di ogni elaboratore

e dipende dalla base di numerazione, dal numero di cifre m destinate alla mantissa

e dal metodo scelto per determinare fl(x). La maggior parte dei sistemi di calcolo

permette di utilizzare due diversi sistemi di rappresentazione dei dati numerici

Esempio 3.11. Dati i valori Xl = 0.2, x2 = 0.00025 e x3

(Xl + x2 ) + x3 = Xl + (x 2 + x3 ) = 0.20103.

0.00078 si ha che

Page 27: Fortran

42

XI(±J (X2

r±l X3)

= 0.2000 10° m(0.2500 10- 3 r±l 0.7800 10- 3) =

= 0.2000 10° l±l 0.1030 10~ 2 =

= 0.2000 10° l±l 0.0010 10° = 0.2010 10°

Il risultato di (Xl mX2) l±l X3 non coincide quindi con quello di xl r±l (X 2 r±l X3):

nel primo caso si è ottenuto un valore che coincide con il risultato esatto a meno

di una quantità dell'ordine di 10- 4, nel secondo l'errore commesso è, al più,

dell' ordine di 10- s.Supponiamo ora di voler sommare i seguenti valori:

Xl = 0.94 10- 4 , X2= 0.26 10- 4 e X

3= 0.1 10°.

Si ha:

(Xl mX2)

r±l X3

= (0.9400 10- 4(±J 0.2600 10- 4) r±l 0.1000 10° =

= 0.120010- 3 I!l 0.100010° =

= 0.000 l 10° r±l 0.1000 10° = 0.100 l 10°

x1(±J (x2

l±l x3)

= 0.9400 10- 4 r±l (0.0000 10° r±l 0.1000 10°) =

= 0.9400 10- 4 r±l 0.1000 10° =

= 0.0000 10° r±l 0.1000 10° = 0.1000 10°.

Il contributo degli addendi xl ed x 2 è completamente ignorato quando la somma

è calcolata aggiungendo il valore di Xl ad x2 I!l x3 .

L'esempio precedente mette in evidenza che, quando si opera in aritmetica

finita, la precisione con cui si determina il risultato, dipende, oltre che dalla pre­

cisione di macchina, anche dall'ordine in cui vengono eseguite le operazioni. Inoltre,

formule matematicamente equivalenti possono dare risultati diversi se utilizzate

in precisione finita.

Esempio 3.12. Si vuoi determinare il punto medio xm di un intervallo di cui sono

noti gli estremi a = 0.651 e b = 0.653. Sappiamo che:

X m = (a + b)/2.

Supponendo di utilizzare in base dieci una rappresentazione finita con tre cifredi mantissa si ha:

Il valore calcolato del punto medio non appartiene all'intervallo ed è quindi

,.

43

completamente sbagliato. Avremmo trovato un risultato più corretto se avessimo

usato la relazione:

X m = b + (a - b)/2:

In questo caso il valore calcolato è xm = 0.652. Infatti:

x m = 0.653 10° Hl (0.65 I 10° El 0.653 10°) O 2 =

= 0.653 10° l±l (- 0.200 10- 2) 02 =

= 0.653 10° r±l (- 0.100 10- 2) =

= 0.653 10° r±l (- 0.001 10°) = 0.652 10°.

Lo studio degli errori di arrotondamento e della loro propagazione è di fonda­

mentale importanza per una corretta interpretazione dei risultati di un qualunque

algoritmo eseguito in precisione finita. Tale studio esula dagli scopi di questo

testo in quanto più pertinente a testi di calcolo numerico (cfr. [9], [lO), [Il)).

Page 28: Fortran

IIIl FORTRAN 77

Il

Page 29: Fortran

~I

4Il linguaggio FORTRAN

4.1. Introduzione

La storia del linguaggio FORTRAN inizia nel 1953, quando la IBM dette inizioal progetto di definizione di un sistema di programmazione per l'allora nuovo

elaboratore 704. Tale sistema doveva permettere di superare gli svantaggi insiti

nell'uso del linguaggio assembly, fra cui essenzialmente il costo notevole di analisi

dei problemi scientifici e l'impossibilità di utilizzo da parte dei non specialisti.

Nel novembre 1954 fu così pubblicato il primo rapporto preliminare sul nuovo si­

stema, chiamato IBM Mathematical FORmula TRANslation system: FORTRAN.

Il progetto iniziale era rivolto all'utilizzo sul 704, a cui si riferiva il primo compi­

latore elaborato nel 1957 e la successiva versione FORTRAN Il; ma il successo

dell'iniziativa fu tale che intorno al 1960 proliferarono versioni del FORTRAN

legate ai diversi elaboratori allora disponibili. Si cominciò allora a sentire l'esi­

genza di definire uno standard del linguaggio da poter assumere come base nella

costruzione dei diversi compilatori: un programma scritto secondo le regole di tale

standard sarebbe stato accettato come sintatticamente corretto da tutti i compi­

latori conformi allo standard. Un primo passo in tal senso fu compiuto ancora

dalla IBM che nel 1962 pubblicò il cosiddetto FORTRAN IV; ma in quello stesso

anno l'American National Standard Institute (ANSI) affidò ad una commissione

la definizione di uno standard che fu definitivamente pronto nel 1966 e che è

noto come FORTRAN 66 (cfr. [13]).

Dal 1966 in poi, in seguito al rapido evolversi degli elaboratori dal punto di vi­

sta dell'hardware e del software, il FORTRAN ha subito grosse trasformazioni.

Nel 1969 l'ANSI decise di formulare un nuovo standard che recepisse le princi­pali e più importanti estensioni del FORTRAN 66 introdotte dai compilatori di

nuova costruzione: la situazione era in così rapida evoluzione che soltanto nel1978 fu approvato il nuovo standard, noto come FORTRAN 77. Il documentoche definisce il FORTRAN 77 [12] descrive due livelli del linguaggio: il Full

Language. detto FORTRAN o FORTRAN 77, ed il Subsct Language che è un

sottoinsieme del Full Language e costituisce lo standard attuale per elahoratori

Page 30: Fortran

48

con capacità di memorie limitate. Le differenze principali tra il Full ed il Subset

Language sono riassunte in appendice A l mentre quelle tra il FORTRAN 77 ed

il FORTRAN 66 verranno messe in evidenza nel corso del testo e riassunte in ap­

pendice A2.

Nel seguito le sigle F77 ed F66 saranno usate per indicare rispettivamente il

FORTRAN 77 ed il FORTRAN 66.

4.2. Alfabeto

L'insieme dei caratteri FORTRAN ossia l'alfabeto del linguaggio è costituito

da:• caratteri alfanumerici: le cifre del sistema decimale (O, l, 2, 3, 4, S, 6, 7, 8, 9)

e le lettere dell'alfabeto inglese (A, B, C, D, E, F, G, H, I, J, K, L, M, N, O, P, Q,

R, S, T, U, V, W, X, Y, Z);

• caratteri speciali: = uguale

+ più- meno

* asterisco

sbarra

parentesi tonda aperta

paren tesi tonda chiusa

punto

apice

spaziatura (blank)

$ dollaro

due punti (non previsto in F66).

Si osservi che il carattere blank può essere usato per migliorare la leggibilità

di un programma; infatti esso non ha alcun significato per il compilatore che lo

ignora sempre ad eccezione di casi particolari che verranno evidenziati in seguito.

Per evidenziare la presenza di un carattere blank useremo talvolta il simbolo v.

4.3. Costanti, nomi simbolici, parole chiave

Un programma FORTRAN è costituito da frasi (o istruzioni) scritte con i

caratteri dell'alfabeto FORTRAN e suddivise in una o più unità di programma.

Tra gli elementi primari che costituiscono una istruzione figurano le costanti,

i nomi simbolici e le parole chiave.

Costanti

Una costante FORTRAN è una successione di caratteri che rappresenta per il

49

compilatore un valore che non deve cambiare durante l'esecuzione del program­

ma. La forma di una costante verrà definita nel capitolo seguente.

Nomi simbolici

Un nome sirnl!2!i~0 è una successione dicaratteri alfanumerici fh~Qeve !!!iziare

con lJ~~)~~t~!~~ deve essere costituita al più da 6 (sei) caratteri. I nomi simbo­'lici sono usati dal programmatore per identificare entità da lui stesso definite

(variabili, matrici, unità di programma, aree di memoria riservate, etc.).

Parole chiave

Nel linguaggio FORTRAN «parola chiave» è sinonimo di «codice operativo».

Una parola chiave è infatti una successione di caratteri alfanumerici a cui il com­

pilatore attribuisce un particolare significato (ad esempio «WRITE» significa

«scrivi», «READ» significa «leggi» e così via) .

Si noti che non esistono in F77 nomi riservati nel senso che la stessa successio­

ne di caratteri può essere usata, ovviamente con significato diverso, sia come nome

simbolico che come parola chiave: il compilatore è in grado di determinare il signi-,ficato corretto in base al contesto in cui la successione di caratteri compare.e

4.4. Frasi eseguibili e non eseguibili

Le frasi FORTRAN si classificano come 1!.~~s{!glii~ili e frasi non eseguibili(cfr. appendice A3): le prime specificano delle azioni che dovranno essere compiute

in fase di esecuzione e vengono tradotte in una o più istruzioni del linguaggio mac­

china; le seconde non descrivono azioni ma forniscono informazioni al compila­

tore specificando, ad esempio, particolari caratteristiche o proprietà dei nomi

simbolici usati (frasi dichiarative o di specificazione) oppure classificando le unità

di programma. J-e fr_~Lnol1_~~ui~illE.9n vengono tradotte in istruzioni del lin-. guaggio macchina.

.b~ frasi che compongono ciascuna unità di programma devono rispet!a..!~.':!~

preciso ordine che impone, ad esempio, che le dichiarative Er~~~dano le eseglJi~

bili (cfr. appendice f\3).

4.5. Etichette

Ad una frase FORTRAN può essere assegnata una etichetta (/abel) in modo chealtre frasi della stessa unità di programma possano farvi riferimento.

Un'etichetta è costituita da una successione di n cifre decimali, l ~ n ~ S, di

cui almeno una diversa da zero. Se n < 5 vengono ignorati i caratteri blank even­tualmente presenti tra una cifra e l'altra, Inoltre le cifre zero eventualmente pre-

Page 31: Fortran

so

senti nelle prime posizioni dell'etichetta non sono significative ai fini della sua di­

stinzione da altre etichette. Così, ad esempio, O1234, l v 234, '171234, 1234'17 in­

dicano la stessa etichetta. E' ovvio che in una stessa unità di programma non pos­

sono esserci due o più frasi con la stessa etichetta. Non è invece considerata un

errore la presenza di etichette superflue ossia etichette alle quali non viene mai

fatto riferimento nel corso della stessa unità di programma; alcuni compilatori

segnalano però come situazione «anomala» la presenza di etichette superflue.

Osserviamo che tutte le frasi FORTRAN possono essere accompagnate da una eti­

chetta ma è possibile far riferimento diretto a11e sole frasi eseguibili ed alla fraseFORMAT (cfr. cap. 13).

4.6. Il formato delle linee

SI

• non è possibile finire una frase FORTRAN ed iniziame un'altra sulla stessa

linea;• il testo della frase va scritto nelle colonne che vanno dalla 7-ma alla 72-ma Iv

\1 comprese;• una frase può essere formata da più linee (fino ad un massimo di venti). La

prima linea è detta linea iniziale e le altre sono dette linee di continuazione;

una linea di contin~azione è caratterizzata dalla presenza di un carattere diverso (j'!

vi' da blank o zero a colonna 6; -

• l'eventuale etichetta di una frase deve essere scritta nelle colonne da I a 5 della

linea iniziale.

:'

t,I

:.1

~

Un programma FORTRAN si presenta fisicamente come una successione di

linee che vengono scritte in modo sequenziale su opportuni supporti.

Ciascuna linea è costituita da una successione di 72 caratteri dell'alfabeto--- - ----- .-

FORTRAN e la posizione di ciascun carattere in una linea è detta _c_ol~nn!1~

I più comuni supporti su cUI vengono scritte le linee di un programma permet­

tono di comporre linee con un numero di caratteri superiore a 72. Gli eventuali

caratteri presenti in una linea a partire da11a colonna 73 in poi sono però ignorati

dal compilatore FORTRAN ai fini della creazione del programma oggetto; essi

possono però essere riprodotti in una lista ovvero in una copia del programma

sorgente. La presenza di caratteri successivi al 72-mo non è quindi «sentita»

in alcun modo dal compilatore FORTRAN il quale, ignorandola completamente,

non la segnala in alcun modo al programmatore; questo può essere fonte di errori

in compilazione e/o in esecuzione non sempre facilmente rintracciabili.

Una linea di un programma è considerata linea di commento e viene del tutto

ignorata dal compilatore quando è interamente costituita da caratteri blank,

oppure quando ha uno dei due caratteri C o * a colonna 1.

Una linea di commento può contenere nelle colonne successive alla primaqualunque carattere, anche non appartenente all'alfabeto FORTRAN, che sia

stampabile, ovvero riproducibile su un supporto esterno quale ad esempio unvideo o un foglio di carta.

Una linea di commento può stare in qualunque punto dell'unità di programma.

Le linee di commento vengono riprodotte nella lista del programma e servono

quindi per facilitare la lettura e la comprensione del programma stesso.

(In F66 una linea è considerata di commento soltanto se ha il carattere C a ~

colonna l. ,

Una linea che non sia linea di commento deve essere composta tenendo pre-senti le seguenti regole:

c o 1t (o tr i'~' /', O

~4' l ~ 4 r ,.,.

~7LL' 'ClOU/'c/',

{OI"l"L"t'Ot1I~ (7unl

12__________ -.1.+--- . _

Page 32: Fortran

5Costanti e variabili:elementi fondamentali di ogni istruzione

Ogni istruzione FORTRAN che elabora un'informazione deve far riferimento

alla locazione di memoria nella quale è contenuta l'informazione stessa. Tale in­formazione può o meno variare durante l'esecuzione del programma: nel primocaso la locazione di memoria deve essere identificata da un nome simbolico

mentre nel sec<.>ndo~ssa !,uò essere identificata da una costante.

5.1. Le costanti ed il loro tipo

In F77 sono previste costanti di tipo diverso: intero, reale. doppia precisione.complesso. logico e carattere. Ogni tipo corrisponde a modalità diverse di rappre­sentazione in memoria del valore identificato dalla costante. La forma di una co­stante ne specifica il tipo ed il valore.

Costanti intere

Si definisce costante intera una stringa di cifre decimali eventualmente prece­duta dal segno + o -. Formalmente una costante intera può essere rappresentatada

~~dove s indica il segno ed n indica una stringa di cifre decimali. Se il segno s manca,la costante si intende essere positiva.

Esempio 5.1. Sono costanti intere le seguenti:

-2 + 37 - 578 1957 - 15878 -I o 3

in quanto nella stringa n compaiono simboli non consentiti (il punto decimale ela virgola).

l b

mentre non lo sono:

- 2.0 1.957 + 0.1 - 15,73

Page 33: Fortran

F

54 55

Il valore rappresentato da una costante intera è memorizzato in una unità di

memoria numerica secondo le modalità viste per la rappresentazione dei numeri

interi.

ciascuna delle quali rappresenta il valore 1O~ 3;

- 4.857E + 03 -.4857E + 04 - 485. 7E I

ciascuna delle Quali rappresenta il valore -4857.

- 4857.EO

Costanti reali

Esempio 5.2. Sono costanti reali nella forma senza esponente le seguenti:

Le costanti reali rappresentano valori che vengono memorizzati in virgola

mobile normalizzata all'interno di una unità di memoria numerica secondo lemodalità viste per la rappresentazione dei numeri reali. Una costante reale può

essere scritta in due modi: senza esponente e con esponente.

Nella forma senza esponente, caratterizzata dalla presenza del punto decimale,

la costante è scritta come

/s n. 011dove s indica il segno mentre n ed m sono stringhe di cifre decimali. Il segno può

mancare ed in questo caso la costante è intesa come positiva. Anche una delle

due stringe n ed m può esser vuota ed in questo caso la stringa mancante è consi­

derata uguale a zero.

+ 0.7 + 23.5 - 0.001 + 0.0 .05 - 1. O.

In F77 è prevista una forma esponenziale senza il punto decimale non consen­

tita in F66. Così sono valide le costanti 1E - 2 per rappresentare 0.0 I oppure

_ 503E - 2 per rappresentare - 5.03.

Le costanti reali sono spesso dette anche costanti reali in precisione semplice

per distinguerle esplicitamente dalle costanti reali in doppia precisione.

Costanti in doppia precisione

Una costante reale in doppia precisione rappresenta un valore che viene memo­

rizzato in virgola mobile normalizzata in una cella costituita da due unità di me­

moria numeriche consecutive.

Le costanti di questo tipo vengono scritte soltanto nella forma esponenziale

con la lettera TI che sostituisce la Eusata per le costanti reali in precisione sempli­

ce. Pertanto una costante in doppia precisione è della forma:

l~-~~mDse Idove s, n, m ed e hanno lo stesso significato visto per le costanti reali.

Nella forma con esponente, caratterizzata dalla presenza della lettera E, la co­

stante è scritta come: Esempio 5.4. Alcuni esempi di costanti in doppia precisione sono i seguenti:

+ 3.875D + 00 387.5D - 02 3875.D - 3 .3875Dl

ciascuna delle quali rappresenta il valore 3.875; le costanti

Isn.mEse\

dove s indica un segno, mentre n, m ed e sono stringhe di cifre decimali. Il signifi­

cato della forma esponenziale è il seguente: + 1000.D + 00 + I.D + 03 I.D3 1 D3

s n . m x l O'" rappresentano invece il valore 1000.

Esempio 5.3. Sono costanti reali nella forma con esponente le seguenti:

ovvero la costante intera e che segue con il suo segno la lettera E ha il signifi­

cato di esponente rispetto alla base dieci e il suo valore è legato alle limitazioni

di overtlow e di undertlow per i numeri reali. Il segno s può mancare ed in questo

caso si suppone che esso sia +; una delle due stringhe n ed m può mancare ed è

considerata uguale a zero.

ciascuna delle quali rappresenta Il valore - 5.03;

Anche per questo tipo di costante va osservato che la versione senza il puntodecimale è valida soltanto in F77.

indica il numero complesso 1.5 + 7.3i

indica il numero complesso 1 - 7i.

(1.5, 7.3)

(1.,-.7EI)

Costanti di tipo complesso

Le costanti di tipo complesso sono usate per rappresentare numeri complessi

e vengono scritte come coppie di costanti reali separate da una virgola e chiuse tra

parentesi:~~':TI~_c()~~nte rappresenta la parte reale del numero complessomentre la seconda rappresenta la parte immaginaria. Così, per esempio:

- 503.E - 2

+ O.OOIE + 00

- 50.3E - 1

.IE - 2+ LE - 3

- 0.503E + 01- 5.03E + 00

+ I.E - 03

Page 34: Fortran

56

Le costanti di tipo complesso sono memorizzate in celle costituite da due uni­

tà di memoria numeriche consecutive.

Costanti di tipo logico

Siccome i valori logici possibili sono soltanto due si hanno due sole costanti

logiche:

.TRUE. e .FALSE.

ossia «vero» e «falso». I punti che accompagnano le stringhe TR UE (FALSE)

fanno parte integrante della costante e non possono essere omessi.

Una costante di tipo logico è memorizzata in una unità di memoria numerica.

Costanti di tipo carattere

Questo tipo di costanti è previsto soltanto in F77; per la loro definizione e uti­

lizzazione si veda il cap. 12.

5.2. Le variabili ed il loro tipo

Una variabile è una cella il cui contenuto (valore) può variare durante l'esecu­

zione del programma ed il nome simbolico che la identifica, detto nume di varia­

bile. la distingue da ogni altra cella della stessa unità di programma. Il nome

simbolico di una variabile deve soddisfare le regole viste nel § 4.3. Sono quindi

corretti i nomi:

A Al NOME X3Y COST SOMMA DIFFE N23

mentre non lo sono:

lA Al. NOME! X3 + Y COjST DIFFERENZA.

Le variabili FORTRAN possono essere di tipo intero, reale, doppia precisio­ne, complesso, logico e carattere. Ad ognuno di questi tipi corrisponde una diversa

rappresentazione in memoria del valore della variabile ed una diversa lunghezza

delle celle destinata a contenerlo. Ogni variabile intera, reale o logica occupa infat­

ti una unità di memoria numerica mentre ogni variabile di tipo doppia precisione

o complesso occupa due unità di memoria numeriche. Le variabili di tipo carat­

tere sono memorizzate secondo modalità diverse che verranno esposte nel cap.

12.

La lettera iniziale di un nome di variabile può essere usata per distinguere

le variabili di tipo intero da quelle di tipo reale. Le variabili reali sono infatti

caratterizzate da nomi che iniziano con una qualunque delle lettere dalla A alla

H o dalla O alla Z; le variabili intere sono invece contraddistinte da nomi che ini­

ziano con una dellelettere I, J, K, L, M, N.

57

Esempio 5.5. Sono nomi di variabili intere i seguenti:

NOME LPI 13 KST AR IND JSOMMA

mentre sono nomi di variabili reali:

OME AMAX SOMMA A I DIFFE STAR.

Se il tipo di una variabile non è intero o reale. esso deve essere esplicitamente

sp~cific!!!Q. Per specificare esplicitamentejltipo di una variabile si usano frasi che

dire~~ di specificazion!.. (dichiarative) di tipu che hanno la 'io~ma

tipo lista

dove:

• tipo sta ad indicare uno dei seguen ti dichiaratori:

INTEGER, REAL, DOUBLE PRECISION. COMPLEX, LOGICAL,

CHARACTER;

• lista indica una successione di nomi di variabile separati da virgole.

L'effetto di una frase dichiarativa di tipo la cui lista sia costituita da nomi di

variabile è quello di comunicare al compilatore che tali variabili sono da consi­

derarsi, nella unit~~i pro~ramma in cui compare la frase dichiarativa, del tipospecificato dal dichiaratore. . ..

Esempio 5.6. La frase

DOUBLE PRECISION RADIX. MAX

serve a specificare che le variabili RADIX e MAX devono essere trattate come va­

riabili doppia precisione e quindi il loro valore verrà memorizzato in celle di lun­

ghezza doppia rispetto a quelle riservate alla memorizzazione di variabili reali.

Ulteriori utilizzazioni delle frasi dichiarative di tipo saranno analizzate nel corso

d.el .testo. Jn ogni caso si deve tener presente che le liste che compaiono in due.Ira,SI dichiarative non possono avere elementi comuni.

Ogni unità di programma può contenere più istruzioni di specificazione di tipo

~a va sempre ricordato che .!!!!!~ le [rasi dichiarative devono essere poste primadi qualunque frase eseguibile (cfr. appendicie A3).

Anche se la lettera iniziale del nome può essere usata per distinguere le varia­

bili reali da quelle intere, può essere comodo usare una dichiarazione esplicita ditipo anche per queste variabili.

Page 35: Fortran

58

Esempio 5. 7. Le dichiarazioni

REAL MEDIA, MINIMO

INTEGER PESO

permettono di utilizzare le variabili MEDIA e MINIMO come reali e la variabile

PESO come intera evitando l'uso di nomi «meno comodi» quali ad esempio

AMEDlA, XMINIM, KPESO.

Si osservi che è abbastanza diffusa l'abitudine di dichiarare il tipo di tutte le

variabili di una unità di programma comprese quelle intere e reali e che alcuni

compilatori possono essere utilizzati in modo da inviare un messaggio di avverti­

mento, se non addirittura di errore, nel caso in cui venga utilizzata una variabile

il cui tipo non sia stato esplicitamente dichiarato. Questa scelta permette di con­

trollare eventuali «errori di battitura» dei nomi di variabile e semplifica le opera­

zioni che devono essere fatte quando si vuoI avere, per esempio, la versione in

doppia precisione di un programma già scritto in semplice.

5.3. L'istruzione IMPLICIT

Le variabili il cui nome non compare in nessuna frase di specificazione di tipo

si dicono di tipo implicito: la lettera iniziale del loro nome determina il loro

tipo.Per fissare il legame tra il tipo di una variabile e la lettera iniziale del suo nome

si usa l'istruzione IMPLICIT che non è prevista in F66. La forma di questa istru­

zione è la seguente:

IMPLICIT tipo I (elenco l), tipo 2 (elenco 2), ...

dove:

• tipo l, tipo 2, etc. sono dichiaratori di tipo (esempio REAL, LOGICAL);

• elenco I, elenco 2, etc. sono liste costituite da una o più lettere dell'alfabeto

inglese ciascuna delle quali è separata dalla successiva mediante una virgola. Un

elenco di lettere consecutive alfabeticamente ordinate può essere indicato median­

te la sua prima ed ultima lettera separata da un segno meno.

L'effetto dell'istruzione IMPLICIT è quello di specificare, mediante i dichiara­

tori, il tipo delle variabili i cui nomi simbolici iniziano con una lettera che compa­re nella specificazione.

L'istruzione IMPLICIT ha effetto soltanto nell'unità di programma che la con­tiene.

Esempio 5.8. L'istruzione

IMPLICIT REAL (I, L-N), INTEGER (A-C)

r59

fa sì che tutte le variabili di tipo implicito i cui nomi iniziano con I, L, M, N

sono di tipo reale mentre quelle i cui nomi iniziano per A, B, C sono di tipo

intero.

L'utilità della istruzione IMPLICIT è evidente quando. per esempio. si vuoI

modificare da reale semplice a reale doppia precisione il tipo di tutte le variabili

di una unità di programma; per far questo basterà utilizzare il comando

IMPLICIT DOUBLE PRECISION (A-H, O-Z).

Per utilizzare correttamente l'istruzione IMPLICIT si deve anche ricordare che

essa deve precedere qualsiasi altra istruzione dichiarativa di tipo e che una dichia­

rativa esplicita di tipo prevale sull'istruzione IMPLICIT.

Esempio 5. 9. La successione di istruzioni:IMPLICIT DOUBLE PRECISION (A-C)

REAL BETA, ALFA

INTEGER CPI

ha l'effetto seguente: tutte le variabili i cui nomi iniziano con le lettere A, B, C

sono di tipo doppia precisione ad eccezione delle variabili BETA ed ALFA che

sono di tipo reale e della variabile CPI che è di tipo intero.

Nel testo, quando non sia esplicitamente indicato, si suppone che il tipo dellevariabili sia implictamente definito dal loro nome.

Inoltre verrà usata la notazione

nome simbolico: valore

per indicare che la variabile, il cui nome simbolico compare alla sinistra dei due

punti, ha il valore specificato alla destra dei due punti; così, ad esempio, I : 5 si­gnifica che la variabile di nome I contiene il valore 5.

Page 36: Fortran

6Le espressioni

Una espressione FORTRAN è una qualunque combinazione di operandi otte­

nuta tramite operatori e parentesi tonde; l'esecuzione delle operazioni indicatedagli operatori dà luogo ad un risultato che viene detto l'a/ore de/l 'espressione.

Si osservi che anche un SlOgOIO operando costituisce una espressione FORTRAN.

Le espressioni FORTRAN si suddividono in aritmetiche, reiazionali, logiche e

carattère.Queste ultime, non previste in F66, saranno trattate nel cap. 12.

6.1. Espressioni aritmetiche

Le espressioni aritmetiche sono utilizzate per ottenere come risultato un valorenumerico. Esse sono costituite da operandi di tipo numerico, quali ad esempio

variabili e costanti di tipo intero, reale, doppia precisione o complesso, e da ope­

ratori aritmetici. Gli operatori aritmetici sono i seguenti:

Operatore

+

*

**

Operazione aritmetica

addizionesottrazionemoltiplicazione

divisioneelevamento a potenza

Osserviamo che in un'espressione aritmetica non sono permessi due operatori

consecutivi, e che l'operazione di moltiplicazione va sempre indicata con il simbo­

lo *. Così, per esempio, sono valide le seguenti espressioni:

1+3 .. 2

mentre sono esempi di espressioni non valide i seguenti:

x * - Y A + - B 5.5 * - l x ** - Y

Page 37: Fortran

( 62 63

e, nell'ambito dello stesso livello di priorità, il calcolo viene eseguito da sinistra

verso destra.

Esempio 6.1. L'espressione 1.0 + 3.0 * 2.0 viene valutata eseguendo prima la

moltiplicazione, che dà come risultato 6.0, e dopo l'addizione fra 1.0 e 6.0; il

risultato finale è quindi 7.0 (cfr. fig. 6.1).

3.0

ti10.0 2.

Y5~/2

Calcolando da sinistra verso destra le addizioni e sottrazioni, il risultato finale è

18.0(cfr. fig. 6.2).

priorità alta

priorità media

priorità bassa

*** e I+e-

3.0 2.0

V1~~1

Valutazione delle espressioni aritmetiche

La valutazione di un'espressione aritmetica avviene usando i contenuti dellecelle di memoria indicate dagli operandi nel modo indicato dagli operatori; per

esempio l'espressione X + Y viene valutata sommando il contenuto della cella

di nome X con quello della cella di nome Y. Se in un'espressione compaiono di­

versi operatori la sua valutazione avviene tenendo presenti le seguenti priorità:

Figura 6.1. Valutazione dell'espressione 1.0 + 3.0 * 2.0. Figura 6.2. Valutazione dell'espressione 5.0 + 10.0/2.0 + 3.0 .. 2 - 1.0.

Esempio 6.2. L'espressione

5.0 + 10.012.0 + 3.0 ** 2 - 1.0

viene valutata eseguendo innanzitutto l'elevamento a potenza che dà come ri­

sultato .lII = 9.0. L'espressione pertanto diventa:

5.0 + 10.0/2.0 + 9.0 - 1.0.

Esempio 6.3. L'espressione A + B/C ** D viene valutata eseguendo prima l'ele­vamento a potenza C ** D; indicato con .0l

Iil risultato di questa operazione,

l'espressione diventa A + B/9f l' viene quindi eseguita la divisione B/9f I otte­nendo un risultato 9f

2; il risultato finale '~3 è ottenuto eseguendo l'operazione

A + .!jI2 (cfr. fig. 6.3).

Viene quindi eseguita la divisione e si ottiene:

5.0 + 5.0 + 9.0 - 1.0.

i~

Page 38: Fortran

,-Jf4 ~ A + ;7i 3

Figura 6.4. Valutazione dell'espressione A + H/C ** D * E-F.

Jf 5

6S

fJtl +-C" D

A + 913 - F

914 - F

C D

VBy~1

V~l

fJt3 fJt 3 +- A + ,rJt2Figura 6.3. Valutazione dell'espressione A + H/C •• D.

fJl3 +- fJl2 * E ~

914 +-A + fJl3~

fJl +- 9t -F5 4

Esempio 6.4. La valutazione dell'espressione

A + B/C ** D • E - F

può essere così schematizzata (cfr. fig. 6.4):

64

911 +- C ** D ~ A + B/ ,0l l • E - F

912 +- B/91 l ~ A + fJt2

• E - F

Uso delle parentesi

L'utilizzazione delle parentesi tonde permette di modificare la priorità di ese­

cuzione delle operazioni aritmetiche in quanto, al momento della valutazione di

una espressione, vengono eseguite per prime le operazioni racchiuse tra parentesi,

Quando una coppia di parentesi è racchiusa in un'altra, l'espressione contenuta

nella coppia più interna viene calcolata per prima.

Esempio 6.5. L'espressione (X + Y) * W viene valutata calcolando prima

,7f l +- X + Y, e poi ,'79 2 +- ,?fl * W; essa corrisponde all'espressione algebrica

(x + y) w. L'espressione X + Y * W, corrispondente invece a x + y w, viene cal­

colata valutando prima ,?fl +- Y * W e dopo .?f2 +- X + ,7f l'

a + bEsempio 6.6. L'espressione algebrica --- deve essere scritta in FORTRAN

ccome (A + B)/C, in quanto l'espressione A + B/C equivale all'espressione algebri­

bca a + e non a quella data (cfr. fig. 6.5).

c

aEsempio 6.7 L'espressione algebrica - è correttamente trascritta in FORTRAN

bca

come A/(B * C), mentre A/B * C corrisponde alla espressione - c (cfr. fig. 6.6).b

Page 39: Fortran

66 67

a+b bFigura 6.7. Calcolo di -- e a + - + d.

c+d c

Elevamento a potenza

In F77 due successivi. elevamenti a~ potenza sono valutati iniziando da quello---- ... -----.-~. -.---. . ~ c

di de;tra: A ** B ** C equivale a a(b). In F66 non è invece consentito l'uso di

du~ elevamenti a pote~~~ ~ucces-siVl senon utilizzando le parentesi; perciò, in F66,

l'operazione a(bc) deve essere trascritta come A ** (B ** C)._~~e..r:e~s!o.!1_e~!g~­

brica (ab)~anUnvec~ tradottasiainFéé chejn,F77 come (A ** B) ** C. Così,

per esempio, se i valori contenuti nelle celle di nome A, B, C sono:

be a+ -.

cc

a+bFigura 6.5. Calcolo di

91,--- A/.r~l

B C

VAtp~1

II,\!

I:

a aFigura 6.6. Calcolo di - e b c.

bc allora

A: 2. B : 2. C: 3.

fig. 6.7).

bcome (A + B)/(C + D), mentre A + B/C + D corrisponde ad a + -+ d (cfr.

c

Esempio 6.8. L'espressione algebricaa + b

c+ddeve essere scritta in FORTRAN

(A ** B) ** C

A ** (B ** C)

A ** B ** C

viene eseguita valutando 2. 2. = 4. e poi 4.3. = 64.;

viene eseguita valutando 2. 3. = 8. e poi 2. 8 = 256.;

non viene eseguita in F66 in quanto considerata

ambigua, mentre in F77 essa equivale alla prece­

dente.

Le parentesi possono anche essere usate per separare due simboli di operatori

aritmetici; così per esempio. dovendo trascrivere l'esnressione algebrica a- b. si

deve scnvere A ** (- B) e J espressione algebrica - ba può essere corretta­

mente scritta come - B * A oppure come A * (- B).

Osserviamo che in F66 una grandezza numerica di qualunque tipo può essere

elevata ad esponente intero, ma soltanto le grandezze reali possono essere elevate

ad esponente reale. In F77, invece, sono permessetuttelecombinazioni di tipo

tra la base e l'esponente.Tatta eccezioneper quelle checoinvolgono i tipi doppia

precisione e complesso. Le combinazioni consentite in F66 e F77 sono riassunte

Page 40: Fortran

68 69

in fig.6.1) e 6.9 rispettivamente, dove I, R, Dp, C indicano i tipi intero, reale,

doppia precisione, complesso.

Dalle figure risulta evidente che, mentre un'espressione come I ** J oppure

AK ** 5 è permessa in qualunque versione del FORTRAN, le espressioni 3 ** 0.5

oppure I ** R non sono valide in F66.

~ Va osservato che in FORTRAN la divisione fra interi dà come risultato la parte IlA

1intera d~!d~~lt~t~che si otterrebbe eseguendo l'operazione in aritmetica reale: trCosì il valore della espressione FORTRAN 1/2 è Omentre 1./2. dà come risul­

tato 0.5. Analogamente:

Nella valutazione delle espressioni intere contenenti una o più operazioni di

divisione è quindi molto importante l'ordine in cui le operazioni vengono effet­4

tuate. Si consideri, ad esempio, l'espressione algebrica - . 3: essa è trascritta cor­3

rettamente nell'espressione FORTRAN intera 4 * 3/3 il cui valore è 4, ma non

nell'espressione intera 4/3 * 3 il cui valore è 3.

k - n(K - N)/M * J.

vale zero qualunque siano i valori di l e J;

vale - l;

vale N se e soltanto se N è pari;

vale N qualunque sia N;

vale zero se M è minore di N in valore assoluto.

1/2 * (l +J)4/(5-8)

N/2 * 2N * 2/2N/M * M

J * (K - N)/M e

Esempio 6.9. Le seguenti espressioni intere

~ l R Dp Cbase

l sì sì sì sì

R sì sì sì sì

Dp sì sì sì no

C sì sì no sì

Figura 6.9. Elevamento a potenza in F77.Figura 6.8. Elevamento a potenza in F66.

~ l R Dp Cbase

l sì no no no

R sì sì no no

Dp sì no sì no

C sì no no no

Il r

Ossen'azione 1. Mentre l'operazione di elevamento a potenza con esponente in­

tero viene di solito eseguita tramite moltiplicazioni ripetute, quella con esponente

reale richiede il passaggio al logaritmo, e quindi un tempo di calcolo maggiore.

Dovendo allora calcolare a3 , conviene usare l'espressione A ** 3 anziché A ** 3.0.

Osservazione 2. La definizione matematica di elevamento a potenza nel campo

reale impone alcune restrizioni: non può essere elevata ad esponente negativo o

nullo un'espressione il cui valore sia zero, e non può essere elevata ad esponente Ireale un' espressione il cui valore sia negativo. .Il \

_____ ~~ j'J

Uso dell'aritmetica intera e reale

Se un operatore aritmetico opera su grandezze dello stesso tipo il risultato di

un'operazione è un valore il cui tipo coincide con quello degli operandi; esso vie­

ne determinato eseguendo l'operazione in aritmetica intera, reale, doppia pre­

cisione o complessa a seconda del tipo degli operandi. Così, ad esempio, 3 + 5

dà come risultato il numero intero g, mentre 3. + 5. dà come risultato il valore

reale 8. che viene memorizzato in virgola mobile normalizzata. Ancora, mentre

l'espressione 30875 + 7874, facendo uso dell'aritmetica intera, può dar luogo

su alcuni elaboratori a fenomeni di overf1ow, l'espressione 30875. + 7874. uti­

lizza l'aritmetica dei reali e il risultato, ovvero il numero 38749., è rappresentato

in memoria come reale.

pur trascrivendo in modo corretto le espressioni algebriche equivalenti jk-n m

e -- j, possono dare risultati numericamente diversi. Per esempio, se i con­m

tenuti delle vanabili sono

K:5 N:3 M:4 J:8

la prima espressione vale 4 (cfr. fig. 6.10) e la seconda vale zero (cfr. hg.6.11).

.~3 9f] +-.0f 2/4

Figura 6.10. Valutazione di ~ * (S - 3)/4.

Page 41: Fortran

j"

70

f

71

Operazioni fra numeri complessi

Le operazioni aritmetiche tra operandi di tipo complesso danno come risultato

un numero complesso. In fig. 6.12 si ricordano le definizioni matematiche delle

operazioni elementari fra complessi intendendo zi = u 1 + i v1 e z2 = u2 + i v2·

Osserviamo che anche nel caso di espressioni non intere può essere fondamenta­

le l'ordine in cui le operazioni vengono effettuate. Infatti il risultato di un'opera­zione fra due numeri reali rappresentabili in macchina può non essere un numero

rappresentabile in macchina, e deve quindi essere approssimato con la sua rappre­

sentazione floating point (cfr. cap. 3). In questa gerarchia il tipo doppia precisione e complesso sono allo stesso li­

vello in quanto essi non possono coesistere in una stessa espressione.

La regola generale che comanda l'esecuzione delle operazioni aritmetiche resta

ancora valida; pertanto se il tipo di due operandi non è lo stesso, quello più debole

~iene automaticamente modificato in quello più forte mediante un'operazione,

detta di conversione, che permette il passaggio da una rappresentazione intem-a .

i ad un'altra. Anche se la possibilità di combinare in un'espressione operandi di

tipo diverso è molto comoda, va osservato che essa dà luogo in generale ad un'ela- l,

borazione più lenta, in quanto l'operazione di conversione «costa» un certo tem­

po macchina.

Operazione RisultatoParte reale Parte immaginaria

I) Doppia precisione, complesso

2) Reale

3) Intero

più forte

1più debole

U1 +u2 v1

+ v2

u1-U2 vI - ":

u1u 2 - v

1v2 U

1V2+V1U2

U1U2+V1V2 U2v

1- v2U

1

Iz21 IZ21

Vu2 + v2 zero2 2

Esempio 6.11. Si consideri l'espressione 1.1 + 2; in essa sono presenti due gran­

dezze di tipo diverso: 1.1 che è reale e 2 che è intera. Siccome l'operazione può

essere eseguita soltanto fra operandi dello stesso tipo, il risultato viene calcolato

in due fasi:

• la costante 2 viene convertita dal tipo intero a quello reale (più forte);

• viene eseguita l'operazione di addizione facendo uso dell'aritmetica reale e siottiene il valore 2.1.

Figura 6.12. Operazioni elementari fra numeri complessi.

Esempio 6.10. Supponiamo che la variabile complessa li contenga il valore

5 + 3i e l2 contenga 2.5 - 1.1 i.

L'espressione l l + l2 dà come risultato un valore complesso la cui parte

reale è data da 5. + 2.5 = 7.5 e quella immaginaria da 3. - LI = 1.9.L'espressione l I + l2 - (8.7, LE - I) dà ancora un valore com plesso la

cui parte reale è uguale a 7.5 - 8.7 = - 1.2 e quella immaginaria è uguale a

1.9 - LE - I = 1.8.

Espressioni aritmetiche miste

Le operazioni aritmetiche di addizione, sottrazione, moltiplicazione e divisio­

ne possono essere eseguite soltanto tra operandi dello stesso tipo. E' però possi­

bile utilizzare in una stessa espressione operandi di tipo diverso dando luogo a

quelle che vengono dette espressioni miste. In queste espressioni le operazioni

vengono eseguite tenendo presente la seguente gerarchia fra i tipi degli operandi:

6Esempio 6.12. Consideriamo l'espressione algebrica "5 a. , ~( fClll 't' ,

Essa può essere trascritta nell'espressione mista 615 * A che, pur essendo

sintatticamente corretta, dà luogo ad un risultato sbagliato: la sua valutazione

infatti prevede innazitutto l'esecuzione della divisione fra interi 6/5 che dà come

risultato il numero intero I; l'operazione successiva I * A è di tipo misto e l'ope­

rando intero l viene convertito nel suo equivalente reale prima di essere molti­

plicato per il contenuto della variabile A. Il risultato dell'espressione FORTRAN6

6/5 * A è quindi A. L'espressione - a può invece essere correttamente tradotta5

come 6 * A/5 oppure 6./5 * A (cfr. fig. 6.13).

Uso delle funzioni intrinseche

Oltre alle operazioni aritmetiche di addizione, sottrazione, moltiplicazione,

divisione ed elevamento a potenza, sono spesso necessarie operazioni più com­

pIesse quali, ad esempio, il calcolo dei logaritmi, di funzioni trigonometriche,

ecc .. Tali operazioni vengono eseguite in FORTRAN usando opportune procedu­

re, dette funzioni intrinseche, ciascuna delle quali è indicata da un nome. Così,

per esempio, la funzione esponenziale è indicata da EXP, la radice quadrata da

Page 42: Fortran

72 73

Figura 6.13. Valutazioni di espressioni miste relative all'esempio 6.12.

• si converte 6 da intero a reale: 6.0

• si calcola 6.0 * A - Risultato reale: ;jfl +- 6.0 * A

si converte 5 da intero a reale: 5.0

• si calcola 3f1/ 5 .0 - Risultato reale: ;'f,f +- :'Jf1/ 5 .

OperazioneNome della Numero di Tipo degli Tipodc:l

funzione argomenti argoment i risultato

{'m l l, R, Dp.C InteroREAL l I, R, Dp,C Reale

Conversione DBLE l I, R, Dp,C Doppia precisioneCMPLX 102 I, R, Dp,C Complesso

Modulo ABS C RealeValore assoluto ABS I, R, Dp Il tipo delRadice quadrata SQRT R, Dp, C risultato coincideEsponenziale EXP R, Dp,C con quello degliLogaritmo naturale LOG R, Dp, C argomenti che,Seno SIN R,Dp,C nel caso siano piùCoseno COS R,Dp,C di uno,<k"l1l10Tangente TAN R,Dp essere tu IliMassimo fra più valori MAX 2 o più I, R,Dp dclIostessoMinimo fra più valori MIN 2 o più I, R,Dp tipo

SQRT (678.36)EXP(Y)MlN (J,. 3 + N, 8)A + SIN (0.5 * TETA)0.5 * (H + A/SQRT(X»B/(ABS (X Y) * EPS)EXP (ABS (H/2»SQRT (13 * C + SQRT(A))

Figura 6.14. Alcune funzioni intrinseche in F77.

SQRT, il valore assoluto da ABS. In fig. 6.14 sono riportate alcune delle principali

funzioni intrinseche disponibili in F77 (per un elenco completo cfr. cap. 14).

Ciascuna funzione opera su uno o più dati, detti argomenti, e fornisce un

unico risultato che può essere utilizzato scrivendo il nome della funzione seguito

da una lista di argomenti racchiusa fra parentesi. Nella maggior parte dei casi è

previsto un solo argomento; quando però gli argomenti sono più di uno, essi de­

vono essere separati da virgole.

Per utilizzare correttamente una qualunque funzione intrinseca è fondamentale

che il numero e il tipo degli argomenti coincida con quello specificato in fig.

6.14; così, ad esempio, SQRT (2) è un'espressione sbagliata in quanto la funzione

SQRT non può essere usata con argomenti di tipo intero. 9ss~.!Yi!!!l1o che un ar­

somentc di tipo sp'!gliatQ non yienecQny~rtit9 autcmaticamente ad un tipo -coj--~

retto, e che inoltre errori di questo tipo non vengono di solito segnalati e generano

quindi risultati imprevedibili.

Sono esempi di espressioni che utilizzano funzioni intrinseche i seguenti:

'1- 6 /5=1

6

!6. A

"cfgf

l

6 5

"cf31'1 AJI\ - 6./5. = l~

"cf

6./5 * A

• si converte 5 da in tero a reale: 5.0

• si calcola 6.0/5.0 - Risultato reale:

9f t +-6./5. = 1.2

• si calcola .3f1 * A - Risultato reale:

91 +- 3f1 * A = 1.2 * A.

6/5 * A

6 * A/5

• si calcola 6/5 - Risultato intero: l

• si converte l da intero a reale: 1.0

• si calcola 1.0 * A - Risultato reale gf +- l. * A

Page 43: Fortran

74 7S

.<al6 - 994 + ~s'

~ C. EXP (X •.'lfl-I.O)

~ C * EXP (.<al 2 - \.0)

~ C * EXP ( fJf 3)

~ C * Y9 4

~1- LOG(X)

,<al 2-X·gpl

91 3 - .rjl2 - \.0

(jf 4 - EXP(.rjl 3)

{jfs-C. fJf4·

Esempio 6.15. Valutazione di C. EXP (X • LOG(X) - 1.0)

~6 - 2.• A

:19 7 - ~S/fJf6'

Esempio 6.16. Valutazione di SQRT(X + SQRT ( 1.0 + X» + X * Y

8l 1- 1.0 + X ~ SQRT(X+SQRT({jfI»+X*Y

9P 2 - SQRT ('~I) ~ SQRT (X + fJf 2) + X * Y

(jf3- X + 91 2 ~ SQRT(.<al3) + X * Y

Come si vede da questi esempi, una qualunque espressione può essere usata

come argomento di una funzione intrinseca; il tipo dell'espressione deve coinci­

dere con uno di quelli specificati dal FORTRAN per l'argomento corrispondente.

L'espressione usata come argomento di una funzione intrinseca può ridursi ad

una costante o ad una variabile come nei primi due esempi, oppure può coin­

volgere operazioni aritmetiche e/o riferimenti ad altre funzioni intrinseche. E'

inoltre premesso utilizzare in un argomento di una funzione intrinseca la fun­

zione stessa (cfr. l'ultimo esempio).Molte funzioni intrinseche in F77 possono avere argomenti di tipo diverso:

in generale il risultato è dello stesso tipo degli argomenti che, se sono più di uno,

devono essere tutti dello stesso tipo. Per esempio, se X è una variabile in doppia

precisione e K una variabile intera, i loro valori assoluti possono essere determinati

rispettivamente da ABS(X) e ABS(K) e. mentre il risultato di ABS(X) è un valorein doppia precisione, quello di ABS(K) è intero; se C è una variabile complessa

il risultato di ABS(C) è un valore reale, il modulo di C.

Osserviamo che lo standard F66 prevede nomi diversi per funzioni che operano

su argomenti di tipo diverso. Così, ad esempio, il valore assoluto di un intero deve

essere calcolato mediante la funzione IABS, di un reale mediante ABS, di una

quantità in doppia precisione mediante DABS, e il modulo di un numero com­

plesso mediante CABS (cfr. cap. 14 e appendice A2).Se in un'espressione aritmetica compare un riferimento ad una funzione in­

trinseca, questa viene valutata prima di effettuare qualunque altra operazione

aritmetica. Da ciò segue che le espressioni che compaiono come argomenti dì uria

funzione saranno le prime ad essere valutate e, se esse utilizzano a loro volta una

funzione, questa avrà la precedenza.

Esempio 6.13. Valutazione di A + SIN (0.5 * TETA)

9P 1 - 0.5 * TETA ~ A + SIN ('~I)

.<al 2-SIN(.<al I) ~A+~2

~3-A+.<al2·

Esempio 6.14. Valutazione di SQRT (B ** 2 - 4. * A * C)/(2. * A)

~1-B**2 ~ SQRT (~I - 4. * A * C)/(2. * A)

992 - 4. * A ~ SQRT (fAI - fA2 * C)/(2. * A)

fA3 - fjf 2 * C ~ SQRT ( fjf I - fjf 3)/(2. * A)

9P 4 - fjf\ - fjf3 ~ SQRT (fA4)/(2. * A)

Si osservi che alcune funzioni intrinseche permettono di eseguire operazioni

di conversione di tipo e possono essere usate per modificare il tipo del risultato

dell'espressione che costituisce il loro argomento. Così, ad esempio, la funzione

REAL permette di convertire in reale quantità di altro tipo e la sua utilizza­

zione può essere esemplificata dalle seguenti espressioni:

REAL (2 + 1)/2 REAL ( I /2) * A

L'esecuzione della prima espressione prevede la valutazione della espressione

intera 2 + I; il suo valore, 3, viene convertito in reale e successivamente diviso

per il numero intero 2. Il risultato della pnma espressione e pertanto 1.5. L'ese­

cuzione della seconda espressione prevede la valutazione dell'espressione in­

tera 1/2; il suo valore, zero, viene convertito in reale e successivamente molti­

plicato per A. Il risultato del1a seconda espressione è pertanto zero qualunque

sia il valore della variabile A.

Page 44: Fortran

76

6.2. Espressioni relazionali

Un'espressione relazionale è costituita da due espressioni aritmetiche legate

da un operatore di relazione (cfr. fig. 6.15):

77

Esempio 6.20. Le espressioni:

B ** 2 .GE. 4. * A * C

B ** 2 - 4. * A * C .GE. O.

Figura 6.15. Operatori di relazione.

Esempio 6.17. X.GT. Y permette di confrontare i valori delle variabili X e Y.

L'espressione è vera se il contenuto della variabile X è maggiore di quello della

variabile Y, altrimenti è falsa.

Si può notare che, non essendo definita una relazione di ordine tra i numeri

complessi, gli unici operatori di relazione permessi con espressioni complesse

sono .EQ. e .NE.

4. * A * C - B ** 2 .LE. O.

sono tutte equivalenti e rappresentano la relazione b2 ~ 4ac.

6.3. Espressioni logiche

Le espressioni logiche sono formate dalla com binazione di valori logici median­

te gli operatori logici .AND., .OR., .NOT., definiti in fig. 6.16; il valore di una

espressione logica è un valore logico.

ABS (E l - E2) .LE. TOLL

El .EQ. E2

4. * A * C .LE. B ** 2

In consegu~nza dell'uso dell'aritmetica finita, è ragionevole aspettarsi che due

espressioni teoricamente equivalenti diano in realtà risultati quasi uguali, ma non

esattamente uguali. Quindi, indicando con E I e E2 i risultati di due espressioni

non intere, l'espressione relazionale

sarà di solito falsa, anche quando matematicamente la relazione deve essere vera.Per prevenire sit~;;'i~ni-ciel-tipo o;a desc-ilitoè opp(";rt~no u~~;~~-~-t;;iTeronza~­

ossia una costante positiva sufficientemente piccola per verificare una relazione

di uguaglianza approssimata: i due valori E I e E2 saranno considerati uguali se

la loro differenza è, in valore assoluto, minore o uguale della tolleranza fissataovvero se:

dove TOLL indica la tolleranza.

IVale la pena di osservare che il valore della tolleranza deve essere scelto con

estrema cura; esso dipende sia dalla precisione con cui si lavora, che dall'ordine idi grandezza di E I ed E2 e, in ogni caso, deve essere tale da evitare una defini­

zione troppo approssimata di uguaglianza.

b

espressioneoperatore di relazione

aritmetica B

Notazione NotazioneSignificato

matematica FORTRAN

.EQ. uguale

*- .NE. diverso

< .LT. minore~ .LE. minore o uguale

> .GT. maggiore;;;. .GE. maggiore o uguale

espressione

aritmetica A

Esempio 6.18. ABStX - Y).LE.l.E - 6 permette 1I1 confrontare il risultato

dell'espressione ABS(X - Y) con la quantità 10- 6; l'espressione relazionale è

vera se la differenza fra i contenuti di X e Y è, in valore assoluto, minore o uguale

di l O" 6, altrimenti è falsa.

Esempio 6.}1). l + J .EQ.K + 3 permette di confrontare il risultato dell'espres­

sione I + J con quello di K + 3. L'espressione relazionale è vera se i due risultati

sono uguali, altrimenti è falsa.

La valutazione di un'espressione relazionale avviene valutando separatamente

le due espressioni aritmetiche e mettendo poi a confronto i loro risultati.

Il risultato di un'espressione relazionale è un valore logico: «vero» se la relazio­

ne specificata dall'operatore è verificata, «falso» altrimenti.

Le due.es2!essio~! aritmetiche che cornpaìonoIri -una" espressione relazionale

posson~~s~~.!~ ~i tipo ~iY~rso: il risultato dell'espressione di tipo più debole èconvertito, prima del confronto, nel tipo più forte. --------.

In F66 le due espressioni aritmetiche devono essere dello stesso tipo.

l

Page 45: Fortran

78

Dalla definizione segue che

II

LI .ANO. L2LI .OR. L2

.NOT. LI

è vero se e soltanto se entrambi i valori logici LI ed L2 sono veri;

è falso se e soltanto se entram bi i valori logici LI ed L2 sono falsi;

è vero se LI è falso, ed è falso se LI è vero.

LI L2 LI .AND. L2 LI .OR. L2 .NOT. LI

vero vero vero vero falsovero falso falso vero falsofalso vero falso vero verofalso falso falso falso vero

r79

Esempio 6.21. LEQ.O .OR. J.GT.I + 3

è valutata come (LEQ.O). OR. (J.GT.(I + 3».

Se I : 3 e J : 5 il risultato dell'espressione è il valore logico falso. mentre se

I : O e J : 5 l'espressione è vera. Notiamo che nel secondo caso è sufficiente valu­

tare l'espressione relazionale LEQ.O per stabilire il risultato; in alcune realizzazio­

ni del FORTRAN verrà valutata anche l'espressione J.GT.(I + 3), in altre sarà

evitato tale calcolo.

Esempio 6.22. 1** 2 .NE. N + M .ANO. 5. + B .GT. SQRT(X)

è valutata come ((I ** 2) .NE. (N + M» .ANO. «5. + B) .GT. SQRT(X»;

supponendo I : 2, N : 3, M : 5, B : 5.5, X : 4, il risultato della espressione è: vero.

Figura 6.16. Gli operatori logici .AND..OR ..NOT.

In F77 sono previsti altri due operatori logici .EQV. e .NEQV. (cfr. fig. 6.17)

tali che:

Esempio 6.23. A.LT.B .ANO ..NOT. L

è valutata come (A.LT.B) .ANO. (.NOT. L); se A : 5.1. B 7.3 e L : .TRUE.,il risultato è: falso.

I valori su CUI gli operatori logici agiscono possono essere costanti o variabili

logiche ed espressioni relazionali; un'espressione logica può quindi contenere

operatori logici, di relazione e aritmetici e nella sua valutazione vengono eseguite

prima le operazioni aritmetiche, poi quelle relazionali e infine quelle logiche,

secondo la seguente scala di priorità:

Figura 6.17. Gli operatori logici .EQV. e .NEQV.

1. + SQRT(2.)

A * 0.5 - 8.0 ** 3

3. ** (1./3) - 5. ** (1./3)(A.GT.O) .OR ..FALSE.

2+3*5

1.5 + 3.141592/2.TRUE..OR ..FALSE.

Esempio 6.24. L .ANO.'A. LE. X .OR. B .GT. 6.15

è valutata come (L. ANO. (A.LE.X» .OR. (B.GT. 6.15); supponendo L: TRUE.,

A : 15.1, X : 17.3, B : 1.0, il risultato dell'espressione è: vero.

6.4. Espressioni costanti

Un'espressione aritmetica, logica o relazionale si dice espressione costante se

non contiene nomi di variabile né riferimenti a funzioni. Inoltre, in un'espressione

aritmetica costante l'operazione di elevamento a potenza è consentita solo con

esponente intero. Sono esempi di espressioni costanti i seguenti:

mentre non lo sono i seguenti:

falsoveroverofalso

più bassa.

priorità

PiÙ['"

è vero se gli operandi hanno lo stesso valore logico;

è vero se gli operandi hanno valore opposto.( \ c!K

-----------------I-f'F'----LI .NEQV. L2

Operatore.NOT.

.ANO .

.OR.I .EQV. e .NEQV.

LI .EQV. L2

LI .NEQV. L2

LI L2 LI .EQV. L2

vero vero verovero falso falso

I falso vero falsoIl falso falso vero

I

i

Le regole suddette possono essere modificate con l'uso delle parentesi in ana­

logia a quanto accade per le espressioni aritmetiche.

Page 46: Fortran

80

Esercizi

6.2 Calcolare il valore delle seguenti espressioni logiche:

6.1 Calcolare il valore delle seguenti espressioni aritmetiche:

81

a(b + c); a(y - b(y - c)); ab + c - a( - 3 + k):

a + bx a+b (a + b) (c + d)d2;

b - cy d a2 _ c2

c+x+y

(_X.: (a: bt5

I ( a ry-3 x2 3 + b

ab+ 3_c; ab + k c.

(36 - 2.)/5 - (4 + 2)

19/4.+3-6

- 2 ** 2/3.

2 ** 2 - 4/5

2 ** 3 - 1./2.

20/2 ** 2(20/2) ** 2 J)~.

19/(5 + 3 - 6)

19/(5 + 3 - 6.)22./(3 + 1) .~ ~

20 - 3 * 4 ((20 - 3) * 415/3*21)

15/(3 * 2)

15./(3 * 2) >,::

- l'

6.4 Calcolare il valore delle espressioni logiche

6.S Trascrivere le espressioni logiche

X + yi+ 2 + h

A+B**3

X + 3.5/Y + 4

AB/C + 2

H * S/Z + (3.1 - H * S)(37.2 * C * Z) / (A + B - C * D/3.1)

A l + X * (A2 + X * (A3 + A4 * X»

L/A ** 2 * (X/Y) ** 3(A + B * Xl/CC + D * Y) - H ** 2 + 3 - AX * (X ** 2 - Y ** 2)/(X ** 2 + Y ** 2)

- 1/(2 * X) + A ** 3/(4. * X ** 3).

X + Y ** I + 2 + H

6.8 Scrivere le espressioni matematiche corrispondenti alle seguenti espressioni:

6.9 Le seguenti espressioni FORTRAN sono sintatticamente corrette, ma non

corrispondono alle espressioni algebriche indicate. Riserivere le espressioniFORTRAN corrette.

(C .OR. D) .AND. F rt:

e LI .NEQV. L2LI .EQV. L2

C .OR. D .AND. F T eI·

1. GE. 2 ( -

(7 + I - 3) .LT. lO I(3. GT. 4) .OR. (lO - 8/2) .LT. 5

(2 ** 3 - 4./5) .LT. 10.1 .AND. 3 .GT. 1 .OR.4 .EQ. (3 + l).

per C : .TRUE., D: .FALSE., F: .TRUE.

NOT.A~T.B.AND.A.EQ.4

I Il ì '\ I

perA :4.,B :5.eperA :5.,B :4.

6.3 Calcolare il valore della seguente espressione logica:l

in altre ad esse equivalenti che facciano uso soltanto degli operatori .AND.,

.OR. e .NOT. (A + B) * CIX + Y(a + b) e

x+y

6.6 Trascrivere le espressioni logiche

.NOT. (A.GT.B .AND. A.LE.C)

.NOT. (A.LE.B .OR. A.GT.C)

in altre equivalenti in cui non si faccia uso dell'operatore .NOT.

6.7 Scrivere le espressioni FORTRAN corrispondenti alle seguenti espressioni

matematiche:

(S + Z) ** 2 + {A * B)/(C * S)

(S + Z) ** 2 + A * B/(C * S)

x * {A * X/B - C * Xl

abs(s + z)2 + ­

c

ab

es

axx

b - ex

Page 47: Fortran

82

aX • A/(B - C) • X x - - cx

b

3 a + bx3./4. R - (A + BX)/CY -r----

4 cy

haxA • B - H + A • X/0.5 • T ab---

0.5t

(ab - h) ax(A • B - H) • A • X/0.5 • T

0.5 t

a(b - h)2A • (B - H) .. 2/A + B .. 2

a + b2

A • B - H •• 2/(A + B) .. 2 (~fa+b

6.10 Usando le opportune funzioni intrinseche, scrivere le espressioni FORTRAN

corrispondenti alle seguenti espressioni matematiche

-1f 3a e.Jbii ;

-1f- e- x+ - sen x; In (a 2 + x2);

2 2 2

- l 2a ( 2 ) 1/2 Il + sen x I;Vx2 + y2 3~'

-;; sen x; In2 l - sen x

sen 3 x cos 2x 7 p; xy l- sen (nx); 6 x

2+) - - - In Ix - y I ;3 3 2 2

e v'3+k max (a, b, c)

Vr2 + (2 1ff- l f .J3 (x 2 + y2) l + min (a 2, b2, c2 _ l)- fg21f

7La frase di assegnazione

7. t. Introduzione

L'istruzione di assegnazione è tra le più importanti in FORTRAN in quanto

permette di memorizzare un valore in una particolare locazione di memoria.

La forma generale di questa frase è:

v = espressione

dove:• v è un nome simbolico di variabile;

• espressione è una espressione FORTRAN.

L'esecuzione di frasi di questo tipo avviene calcolando prima il valore del­

l'espressione e memorizzando poi tale valore nella cella identificata dal nome

v. Il simbolo = ha quindi in FORTRAN un significato completamente diverso

da quello matematico: esso permette di definire il contenuto della cella di memo­

ria individuata dall'identificatore v che compare alla sua sinistra attribuendogli

il valore dell'espressione scritta alla sua destra; esso è quindi equivalente al simbo­

lo <- visto nel linguaggio dei diagrammi a blocchi. Mediante una frase di asse­

gnazione è allora possibile indicare quali operazioni si vogliono eseguire e su

quali operandi ed in quale locazione di memoria si vuoI trasmettere e conservare

il risultato ottenuto. Tenendo presente il tipo del contenuto di una cella di me­

moria è possibile distinguere tra assegnazione aritmetica, assegnazione logica ed

assegnazione tra stringhe di caratteri. Esaminiamo qui i primi due tipi riman­

dando al cap. 12 l'analisi del terzo tipo.

7.2. Assegnazione aritmetica

Si tratta di una istruzione del tipo:

v = espressione aritmetica

dove v è l'identificatore di una variabile intera, reale, doppia precisione o com­plessa.

Page 48: Fortran

848S

Esempio 7.2. Supponendo che le variabili I, N, A, B contengano i valori:

Negli esempi che seguono supporremo di valutare una espressione reale con una

precisione Ero ::;: 10- 6 e una espressione doppia precisione con Ero ::;: 10- 16.

Esempio 7.1.A = 1.85

1=4

XI = Z

effetto: il valore 1.85 è memorizzato in A

effetto: il valore 4 è memorizzato in I

effetto: il contenuto di Z è copiato in X l.

Esempio 7.5. L'effetto della frase di assegnazione

v = 1./3. + 1./3. + 1./3.

è quello di memorizzare in V il valore 0.999999 dell'espressione reale a destra

del segno =. Se D è il nome di una variabile in doppia precisione il suo contenuto,

dopo l'esecuzione della frase

0= 1.00/3.00 + 1.00/3.00 + 1.00/3.00

è 0.9999999999999999.

I : lO N: 3 A: 1.5 B: 0.5

indichiamo, accanto ad ogni frase di assegnazione, il suo effetto

A=BH = A + 10.5

Esempio 7.3. Supponendo che A e B contengono i valori usati nell'esempio

precedente, l'effetto della esecuzione sequenziale delle frasi:

Esempio 7.7. I = X + Y + ZL'espressione è reale mentre è una variabile intera. Supponendo che sia

X : 4.5, Y: 0.0, Z : 1.0, il valore dell'espressione è 5.5 e ad I viene assegnato

il valore 5 = INT (5.5).

Esempio 7.6. A = 7/3 * K.L'espressione è intera mentre A è il nome di una variabile reale. Supponendo

che K : 3 il valore dell'espressione è 6 e il valore 6.0 = REAL (6) viene memoriz­

zato in A.

Il~g__c!~lla v~rilÙ)ik_dicui v è l'identificatore può essere diverso da quello

dell'espressione aritmetica. In questo caso la frase di assegnazione è detta di

assegnazione mista e la sua esecuzione avviene secondo lo schema seguente:

• l'espressione viene valutata in base al tipo degli operandi che la compongono;

\

' il .tipo ~ell'identificatore v non influenza in alcun modo il calcolo dell'espressione

aritmetica;

• il risultato dell'espressione viene automaticamente convertito nel tipo di v

mediante l'opportuna funzione intrinseca di conversione (lNT, REAL, OBLE,

CMPLX) e viene quindi memorizzato nella locazione di nome v (ulteriori det­

tagli sulle funzioni di conversione sono dati nel cap. 14).

H: 11.5B : 0.5

il valore 13 di lO + 3 è memorizzato in IPN;

il valore 1.0 di (1.5 + 0.5)/2 è memorizzato in H;il valore 4.0 di 1.5 + (2. * 0.5 + 1.5) è memorizzato

in A:il valore 160 di lO + 150 è memorizzato in I

A: 0.5

è il seguente: con la prima frase viene cancellato il contenuto 1.5 di A e sostituito

da quello di B ovvero da 0.5; con la seconda viene valutata A + 10.5 ovvero

0.5 + 10.5 e il suo risultato Il.O è memorizzato in H. Quindi, dopo l'esecuzione

di queste due frasi si ha:

I = I + 150

IPN = I + N

H = (A + B)/2

A = A + (2. * B + A)

••

Esempio 7.4. Supponiamo che vengano eseguite sequenzialmente le frasi:

N = 2l = N + ll = N + l - 5 * l ** 2

Con la prima istruzione il valore 2 è memorizzato in N: con la seconda viene va­

lutata l'espressione intera N + I e il suo valore, 3, è memorizzato in I; con la ter­

za viene valutata l'espressione N + I - 5 * I ** 2 ovvero 2 + 3 - 5 * 3 ** 2 il cui

risultato, - 40, è assegnato come nuovo contenuto di I.

b

Esempio 7.8. V = 1.0 - 12 + A.

Supponendo che A e V siano variabili reali e che A : 1.0, l'espressione viene

valutata in doppia precisione in quanto vi compare come operando la costante

I.D - 12. Il risultato dell'espressione doppia precisione .100000000000 10000 + I

viene troncato e memorizzato nella cella V il cui contenuto diviene quindi

.IOOOOOE + OI = REAL (.100000000000 IOOOD + I).

In fig. 7.1 si riassumono le possibili frasi di assegnazione aritmetica mista

previste in F77; si può notare che sono proibite situazioni che prevedono la con-

Page 49: Fortran

r86 87

versione doppia precrsione - complesso o viceversa. In F66 sono proibite anche

le frasi di assegnazione mista in cui la variabile v oppure l'espressione aritmetica

sono di tipo complesso.

/espressione realevariabile intera = - espressione doppia precisione

"'--espressione complessa

espressione interavariabile reale =~espressione doppia precisione

"<, espressione complessa

dopo l'esecuzione delle prime due frasi di assegnazione la variabile T I contiene

il valore «vero» mentre T2 contiene il valore «falso». Il contenuto di T I viene

modificato dalla frase successiva. Essa viene eseguita valutando prima il valore

dell'espressione logica TI .AND.T2 che, essendo T2 falso, dà come risultato lo­

gico .FALSE.; tale valore viene quindi assegnato come contenuto di T I.

Osserl'azione. Nella pratica si presenta spesso la necessità di scambiare il conte­

nuto di due celle di memoria dello stesso tipo. Indicate con A e B le due celle,

la successione di istruzioni

""espressione interavariabile doppia precisione =/

""'-espressione realenon ha l'effetto voluto, che è invece ottenuto dalla successione

/espressione interavariabile complessa =

""'-espressione reale

Figura 7.1. Assegnazioni uitmetiche miste previste in F77.

7.3. Assegnazione logica

E' possibile assegnare il risultato di una espressione relazionale o logica ad una

variabile di tipo logico v mediante la frase:

dove S è il nome di una cella di memoria «ausiliaria» dello stesso tipo di A e B.

in cui si «salva» il contenuto di A per poterlo poi assegnare a B.

In generale, nel seguito, con la frase «scambia A con B» si indicherà una suc­

cessione di operazioni del tipo sopra indicato.

v = espressione logica

la cui esecuzione implica la valutazione della espressione indicata e la assegnazione

del suo valore (cvero» oppure «falso») alla variabile logica v.

Esercizi

7.1. Dire quali delle seguenti frasi di assegnazione non sono corrette e perché:

I = 1+ K; 49 = K L = A + B/C; A + C ** 2 = D ;

R = SQRT(X + Y); A + B = 0.5 + H

7.2. Scrivere le opportune frasi di assegnazione per memorizzare la parte intera

del valore di ciascuna delle seguenti espressioni aritmetiche:

7.3. Scrivere le opportune frasi di assegnazione per memorizzare in floating point

i valori delle espressioni dell'esercizio 7.2.

33a -

2j - 5

(sin (x) + cos (x»2

sin 2(x) + cos 2(x)

a+~

LOGICAL TI, T2TI = .TRUE.T2 = .FALSE.TI = TI .AND. T2

LOGICAL VAL, FLAGVAL= .TRUE.FLAG = .FALSE.

dopo l'esecuzione di queste frasi la cella di memoria chiamata VAL contiene il

valore logico «vero» e quella indicata con FLAG il valore «falso».

Esempio 7. 9.

Esempio 7.10.

Page 50: Fortran

88

7.4. Dire quale valore è assegnato per effetto delle seguenti frasi:

A = 1/2 + 3.5

M = A/2 + 5/2

M = (A + 5)/2

B = REAL(l)/2 + 3.5

con I : 3

conA:5.

con A :4.

con I : 3.

8Alcuni semplici programmi

7.5. Supponiamo di usare un elaboratore nel quale, dato x, fl(x) è ottenuto

mediante troncamento; dopo l'esecuzione sequenziale delle frasi:

R = 3.

X = l./R

L = 3. * X

M = R * X

N=X+X+X

le variabili L, M ed N contengono il valore zero. Perché?

7.6. Dire quali delle seguenti frasi di assegnazione non sono corrette e perché

(solo i nomi di variabile che iniziano con la lettera L sono di tipo logico):

L = A.AND.LI; A.LT.B + 5. = LA; A = Ll.OR.L2

L = A ** 2.GT.5 ..OR ..NOT.L.; LI = .NOT.(A.RQ.B);

LI = .NOT.(A.EQ.B); A.NE.B = LI; L4 = Ll.AND.(L2.0R.L4).

7.7. Scrivere le opportune frasi di assegnazione di tipo logico per memorizzare

il risultato della valutazione delle seguenti espressioni logiche informali:

«A è maggiore di B e C non è minore di D»

«non LO oppure L l»

<<1 è uguale a l O oppure A è minore o uguale a l.E-5».

7.8. Descrivere tramite frasi di assegnazione le seguenti situazioni:

«L è vera se LI è vera e L2 è falsa, altrimenti è falsa»

«L è falsa se LI è vera oppure A è maggiore di B, altrimenti è vera».

8.1. Introduzione

Abbiamo visto nei capitoli precedenti quali siano gli elementi fondamentali

costituenti le frasi del linguaggio FORTRAN: le costanti e le variabili. Tramite

questi elementi, insieme agli operatori aritmetici, logici e di relazione, si possono

costruire le espressioni. Finalmente, tramite le espressioni, si può realizzare

l'operazione di assegnazione.

Prima di passare ad esaminare altre fondamentali frasi FORTRAN quali quelle

di controllo, vogliamo dare in questo capitolo alcuni esempi di programmi comple­

ti per la cui costruzione possediamo già alcuni strumenti. Osserviamo che, avendo

come unica frase eseguibile quella di assegnazione, siamo in grado di scrivere sol­

tanto programmi che realizzano una sequenza di calcoli e che portano a definire

il valore di alcune variabili. Tali programmi hanno un senso molto particolare:

essi infatti calcolano sempre gli stessi valori in quanto non possono acquisire dati

di volta in volta diversi e, d'altra parte, non riescono a fornire i risultati calcolati;

in una parola, manca loro l'interfaccia con il mondo esterno costituita dalle opera­

zioni di ingresso/uscita. Con le operazioni di ingresso si possono acquisire dati

di volta in volta diversi e con le operazioni di uscita possiamo visualizzare i risul­

tati.

Per poter scrivere un programma reale, è infine indispensabile usare delle op­

portune frasi che ne indichino la fine. L'inizio di un programma FORTRAN è

invece automaticamente indicato dalla sua prima frase.

8.2. Frasi di ingresso/uscita guidate dalla lista

Nei capitoli 13 e 18 verranno trattate estensivamente le diverse frasi di ingres­

so/uscita previste in F77. Per il momento. allo scopo di poter scrivere qualche

semplice programma, mtrocuciarno le frasi di ingresso/uscita guidate dalla lista

(non previste in F(6): csse permettono di leggere dati o visualizzare risultati ser­

vendosi delle unità di ingresso () di uscita standard, definite dal sistema di calcolo

Con cui si lavora, senza specificare nel programma il modo in cui i dati o i risultati

Page 51: Fortran

r90 91

devono essere forniti.

La frase di ingresso guidata dalla lista ha la forma seguente0.5. Alcune forme in cui i dati possono essere forniti al momento dell'esecuzionedella frase sono le seguenti:

PRINT ., lista-di-uscita

Esempio 8.3. Sono esempi di frasi di uscita guidate dalla lista i seguenti:

(a) 7 15/0.05 0.5(b) 7, 15 /(c) 7

15

/

7 15 0.05 0.57, 15,0.05,0.57, 15.5 E-l, 0.5

7

155.E-2

5.E-l

(a)

(b)

(c)

(d)

La precedente frase di lettura può essere usata per assegnare un valore alle

sole variabili Kl e K2; per questo è sufficiente fornire i dati, ad esempio, in unadelle forme seguenti:

Se si vogliono leggere n valori uguali a una costante c, è possibile scrivere su

una linea un simbolo della forma n. c invece di scrivere n costanti uguali a cseparate da virgole o da caratteri blank.

In analogia con la frase READ ., esiste in F77 la frase di uscita guidata dallalista che ha la forma:

dove:

• PRINT è la parola chiave;

• Iista-di-uscita è una lista di espressioni FORTRAN separate da virgole. For­me più generali di lista-di-uscita sono definite nel cap. 13.

PRINT *, A, BPRINT *, A, B, A + B, A .. 2 - B .. 2PRINT -. N, X, SQRT (DELTA)PRINT -. ABS(X).GT.EPS

L'effetto della frase PRINT. è il seguente: vengono calcolati i valori delle

espressioni che compaiono nella lista; questi valori vengono poi riprodotti sulper assegnare alle variabili K l, K2, X ed Y rispettivamente i valori 7, 15, 0.05,

READ ., lista-di-ingresso

READ., Kl, K2, X, Y

Esempio 8.2. Supponiamo di usare la frase

I dati in lettura possono essere disposti su una o più linee (righe su una tele­

scrivente, schede perforate, etc.) e sono separati da caratteri blank o da virgole:

il primo dato inizia con il primo carattere non blank e termina quando compare

un altro carattere blank o una virgola; il secondo dato, se esiste, inizia dal successi­

vo carattere non blank e così via. L'esecuzione di una frase di lettura guidata dalla

lista fa sì che vengano lette tante linee quante ne sono necessarie per assegnare un

valore a tutte le variabili della lista. L'operazione di lettura viene però interrotta

se si incontra su una linea un carattere / (sbarra): in questo caso le eventuali

variabili della lista a cui ancora non è stato assegnato un valore, mantengono

quello che avevano prima dell'inizio dell'operazione.

Notiamo infine che ogni operazione di lettura inizia con una nuova linea.

A = 0.01B = -0.001

1=5.

Esempio 8.1. Con l'istruzione

READ .,A, B, I

si leggono dal mezzo di ingresso standard tre valori numerici, due reali e uno inte­

ro, che vengono memorizzati nelle celle di nomi A, B, I. Supponiamo ad esempio

che i dati forniti siano, nell'ordine, 0.0 l, - 0.00 l, 5; allora la frase di lettura ha

lo stesso effetto, ai fini della definizione dei valori di A, B, I, delle tre istruzioni

di assegnazione

dove:

• READ è la parola chiave:

• Iista-di-ingresso è una lista di nomi simbolici separati da virgole (forme più

generali di una Iista-di-ingresso verranno viste nel cap. 13).

L'effetto dell'esecuzione della frase READ. è il seguente: vengono letti tanti

valori quanti sono i nomi simbolici presenti nella lista; il primo valore viene asse­

gnato alla prima variabile, il secondo alla seconda e così via. I valori in ingresso

devono essere sotto forma di costanti FORTRAN e devono accordarsi in ordine e

tipo con le variabili della lista.

Page 52: Fortran

92

mezzo di uscita standard (video, telescrivente, stampante, etc.) in un formato

che dipende dal tipo di ciascuno di essi e dalla particolare realizzazione del

FORTRAN. Così, per esempio, il risultato di un'espressione aritmetica reale può

venir stampato nella forma con o senza esponente in base al suo ordine di gran­

dezza: di solito vengono visualizzate un numero di cifre coerente con la precisio­

ne di macchina. In ogni caso, in uscita i dati di tipo numerico sono preceduti e

seguiti da caratteri blank che ne facilitano la lettura. Ogni operazione di uscita

inizia su una nuova linea e crea tante linee quante ne sono necessarie per stam­

pare tutti i valori previsti dalla lista di uscita.

Esempio 8.4. La frase

PRINT*, X, Y, X - Y

fa sì che vengano riprodotti sul mezzo standard i valori di X e Y e la loro dif­

ferenza, risultato dell'espressione X - Y.

Negli esempi che seguono faremo spesso uso di liste di uscita contenenti costan­

ti di tipo carattere che sono costituite in generale da una stringa di caratteri

alfanumerici e/o speciali delimitata da apici (cfr. cap. 12). Osserviamo che una

coppia di apici consecutivi all'interno di una costante di tipo carattere viene ri­

prodotta in stampa come un unico apice, mentre gli apici che delimitano la

stringa non vengono riprodotti in stampa.

Esempio 8.5. Supponendo che sia A : 2, B : 3 ed R: - 1.5 e che la precisione di

macchina sia dell'ordine di 10- 6 la frase

PRINT., 'LAVSOLUZIONEvDELL"EQUAZIONE', A, '.X+',B, '= O.E"', R

produce la linea di stampa:

LA SOLUZIONE DELL'EQUAZIONE 2.000ooo.X + 3.000000 = O.E' - 1.500000

Se invece è A : 2 x 10 9 , B : 3 x 10 9 ed R : - 1.5 la stessa frase di uscita dà

luogo alla seguente linea di stampa:

LA SOLUZIONE DELL'EQUAZIONE 2000000 E +09.X +3.000000 E +0.9 =O.E' -1.500000

8.3. Le istruzioni PROGRAM, STOP e END

Vogliamo ora scrivere un programma che legga due numeri reali a, b conb

a '* O, calcoli la soluzione r = - - dell'equazione ax + b = O, e la stampi.a

93

PROGRAM RADICIC PROGRAMMA CHE CALCOLA LA SOLUZIONE DELL'EQUAZIONEC AX + B = O CON A.NE.O

READ., A, BR = - B/APRINT., :LAVRADICEVDELL"EQUAZIONE', A, '.X +', B: = OV['"PRINT., ••••• ', R, ' ••••*STOPEND

Nel programma ora scritto compaiono alcune nuove istruzioni: la prima e le

ultime due.

Istruzione PROGRAM

PROGRAM RADICI è la frase che dà il nome (RADlC l) al programma. La

forma generale dell'istruzione PROGRAM è la seguente:

PROGRAM nome

dove:

• PROGRAM è la parola chiave che identifica la frase;

• nome è un nome simbolico che non deve essere usato in nessun'altra istru-

zione del programma.

~a frase PROGRAM non esiste-in F66 e il suo uso in F77 è facoltativo in quan­

to Il nome che con essa si assegna serve esclusivamente per distinguere un pro­

gramma da un altro.

Quando è presente, la frase PROGRAM deve precedere ogni altra istruzione.

Istruzioni STOP e END

Le ultime due frasi del programma RADIC l ne indicano la fine. La frase costi­

tuita ~alla sola parola chiave STOPln~qi(,:~ k[ine logica del programma; la sua

esecuzione fa sì che l'esecuzione del programma termini.

. La frase costituita dalla sola parola chiave END deve essere l'ultima istruzionedi ogni '1' d' .'. 111 UI1l a .1 programma; essa e ~I1.~)ras~ non eseguibile ed ha lo scopo di in-

dicare al compilatore la fine fisica dell'unità di programma.

Osserviamo che in F77, ma non in F66. la successione di istruzioni

STOP

END

è equivalente alla sola Istruzione END.Osservi. . I h"rviarno 1110 tre c e 111 un programma possono essere presenti più frasi

STOP, se è richiesta l'interruzione dell'esecuzione in più punti distinti,

La frase STOP può essere usata anche nella forma

STOP n

b _

Page 53: Fortran

94

dove n è una costante intera costituita al più da 5 cifre (o, in F77, una costante

di tipo carattere). Quando l'istruzione STOP n viene eseguita, la costante n èdisponibile per qualche scopo dipendente dalla particolare realizzazione del

FORTRAN; di solito essa viene visualizzata sul mezzo standard di uscita e può

servire per individuare in Quale punto il programma è terminato quando vi siano

più punti di uscita.,

'I Riassumendo, in un programma scritto in F77 possono esserci nessuna, una, ~

/

. o più frasi STOP, mentre deve essercene almeno una se il programma è scritto in .

F66. In ogni caso ogni unità di programma deve terminare con la frase END.

In fig. 8.1 sono riportate le modificazioni dello stato della memoria dovute

all'esecuzione del programma RADICI, nell'ipotesi che i valori letti siano a = 0.01

e b = 83.24 e che la precisione di macchina sia dell'ordine di 10-6 .

r95

Esempio 8.6. Un risultato analogo a quello del programma RADICI per quanto

riguarda la gestione delle operazioni di ingresso/uscita, ma non per quanto riguar­

da la memoria, si ottiene con il seguente programma.

PROGRAM RADIC2READ -. A, BPRINT *, 'LAvRADICEvDELL"EQUAZIONE', A, '*X +', B: = OvE'"PRINT *, '****., - B/A, '****.STOPEND

In questo programma manca l'assegnazione alla variabile R del valore - B/A,

che invece viene direttamente stampato per effetto dell'ultima frase PRINT.

8.4. L'istruzione PARAMETER

Memoria

A B R ...

- - - -

rno.ou n(83.24) - -

nro.on n(83.24) 11(- 8324.) -

nro.on 11(83.24) n(- 8324.) -

n(OOI) n(83.24) 11(- 8324.) -

Stato iniziale

Dopo l'esecuzione della frase READ

Dopo l'esecuzione della frase R = - BIA

Dopo l'esecuzione delle frasi PRINT

Stato finale, al momento dell'esecuzionedella frase STOP

Supponiamo di voler scrivere un programma in cui. dato un valore x > I, sicalcola e si stampa il valore y = f(x), con

I+n'f( x) = x 2 - 2 n'x + -- - 2 n'

Inx

dove n' è un parametro reale che per il momento fissiamo uguale a 0.1. Il risul­

tato desiderato può essere ottenuto con uno dei due programmi seguenti:

PROGRAM ALFAIREAD -. Xy = X * X - 2. * 0.1 * X + (1. + O.1)/LOG(X) - 2. * 0.1PRINT -. 'X = t x.v =', YSTOPEND

Dati in ingresso

0.01 83.24

Linee di stampa

LA RADICE DELL'EQUAZIONE O.OiOOOO *X + 83.24000 = O E'- 8324.000 *****

figura 8.1. Esecuzione del programma RADIC 1.

PROGRAM ALF A2ALFA = 0.1READ -. X

Y = X * X - 2. * ALFA * X + (l. + ALFA)/LOG(X) - 2. * ALFAPRINT *,'X =', x.v = " YSTOPEND

La differenza principale fra i due programmi è la seguente: in ALFA I si è in­

serito il valore 0.1 direttamente nell'espressione FORTRAN il cui risultato viene

memorizzato in Y; in ALFA2 si è introdotta una variabile, ALFA, a cui si assegna

Page 54: Fortran

96

il valore 0.1, e che viene usata nell'espressione. E' ovvio che ALFA2 è un pro­

gramma più flessibile di A LF Al; infatti è possibile usarlo per valori diversi del

parametro Q' semplicemente intervenenuo sulla frase di assegnazione ALFA = 0.1,

anzichè sulla frase, ben più complessa, che definisce Y. In F77 è possibile defi­

nire ALFA come nome simbolico della costante 0.1 mediante la frase dichiara­

tiva PARAMETER, la cui forma è la seguente:

cC

PROGRAM CERCHIOSTAMPALA LUNGHEZZA DELLA CIRCONFERENZAE L'AREA DEL CERCHIOPARAMETER (PI = 3.141592, DUEPI = 2. * Pl)READ -. RAGGIOPRINT -. 'RAGGIO =', RAGGIOPRINT *, 'LUNGH.vCIRCONFERENZA = ,DUEPI * RAGGIOPRINT -. 'AREA =', PI * RAGGIO ** 2STOPEND

97

dove:• PARAMETER è la parola chiave che identifica la frase;

• Pl"'" Pn sono nomi simbolici;• e

l, ... , e

nsono espressioni costanti (cfr. §6.4). Se P j è di tipo carattere, logi-

co, o numerico, ei

deve essere di tipo carattere, logico o numerico rispettivamente.

Per effetto dell'istruzione PARAMETER, il nome Pi è un nome simbolico di

costante il cui valore è il risultato dell'espressione e i che gli viene associato se­

condo le regole dell'assegnazione. Se in un'istruzione PARAMETER compare

un'espressione contenente un nome simbolico di costante, questo deve essere

stato definito precedentemente nella medesima o in un'altra frase PARAMETER.

Un nome simbolico di costante è un nome di costante a tutti gli ~!'fet~!

avendo la «forma» di un nome di variabile; esso può quindi essere usato in una

frase FORTRAN allo stesso modo di una costante, salvo il fatto che non può

essere parte di una costante (ad esempio, parte reale o parte immaginaria di una

costante complessa), e neppure di una specificazione di formato (cfr. cap. 13).

Si osservi inoltre che, in quanto nome di costante, il valore di un nome simbo-I

{\'i lico di costante non può essere modificato mediante, ad esempio, frasi di asse-I \\

gnazione o di lettura o mediante altre frasi PARAMETER. I.In quanto dichiarativa, l'istruzione PARAMETER deve precedere tutte le frasi

eseguibili dell'unità di programma in cui compare. Per quanto riguarda la posizio­

ne della PARAMETER rispetto alle altre frasi dichiarative, si veda l'appendice

A3.

Esempio 8. 7. Sono esempi corretti di utilizzo della istruzione PARAMETER i

seguenti:

LOGICAL VERO, FALSOPARAMETER (VERO = .TRUE., FALSO = .FALSE)PARAMETER (EPSM = lE ~ 06, EPS = IO *EPSM)PARAMETER (ALFA = 0.1, BETA = ALFA * EPS)

Esempio 8.8. Nel programma seguente SI definiscono i due nomi simbolici di

costante l'I e DUEPI; eSSI vengono usati nelle espressioni aritmetiche che figurano

nelle istruzioni di stampa.

L

8.5. Altri esempi

Vediamo qualche altro semplice programma in cui si utilizzano le frasi

FORTRAN fin qui incontrate.

Esempio 8.9. Dati due numeri II' 12 > O si vuoi calcolare e stampare l'area ed il

perimetro del rettangolo di lati II e 12 e del quadrato di lato uguale al minimo fra

Il e 12,

PROGRAM GEOMREAL LATOI, LATm, LATO

C LETTURA DEI DATIREAD *, LATOI, LATm

C CALCOLO DEL PERIMETRO E DELL'AREA DEL RETTANGOLOPRETT = 2. * (LATOI + LAT02)ARETT = LATOI * LAT02

C CALCOLO DEL PERIMETRO E DELL'AREA DEL QUADRATOLATO = MIN (LATOI, LAT02)PQUAD =4. * LATOAQUAD = LATO * LATO

C STAMPADEI RISULTATIPRINT *, 'ILvPERIMETROvDELvRETTANGOLOvDIvLATI'

LATOI, LAT02, 'E":', PRETT 'PRINT *, 'LAvSUAVAREAvE":', ARETTPRINT *, 'ILvPERIMETROvDELvQUADRATOvDI LATO', LATO,

'E":' PQUADPRINT *, 'LAVSUAVAREAVE":', AQUADSTOPEND

Esempiu 8. JO Il seguente programma calcola un valore approssimato per sen x,

dove x è espresso in radianti, come somma dei primi cinque termini dello sviluppo

111 serie di potenze

Lx2k ~ I x3 x5 x7 x'l

se n x = (- l )k X - - + - + --

k=O (2k + l)' 3' 5' 7' 9'

Page 55: Fortran

(98

ccc

PROGRAM SENOAPPROSSIMAZIONE DEL SENO DI UN ANGOLO DIX RADIANTI TRAMITE LA SOMMA DEI PRIMI CINQUETERMINI DELLO SVILUPPO IN SERIE DI POTENZE

PRINT ., 'SCRIVlvILvVALOREvDlvX vINvRADIANTI'READ., XTI =XT2 = TI • X/2.• X/3.T3 =T2 • X/4.• X/S.T4 = T3 • X/6. • X/7.T5 = T4 • X/8.• X/9.PRINT., 'ILvSENOvDl', X, 'E" CIRCA'PRINT., 'u., TI - T2 + T3 .- T4 + T5, '•••STOPEND

r99

dove ft x) è definita da:2- n

8.4. Individuare gli eventuali errori nelle seguenti frasi:

PARAMETER (RAD 2 = SQRT (2.»

PARAMETER (EINV = l./E, E = 2.7182)

PARAMETER (SO M = 0.5, UNO = r., ZERO = O)

PARAMETER (N = in N2 = N. N)

8.5. Indicare i valori delle variabili A, B, N, NP e J dopo l'esecuzione della frase

Si noti che l'esecuzione di questo programma è prevista in modo interattivo,

in quanto la prima istruzione prevede la stampa sul mezzo standard del messaggio

SCRIVI IL VALORE DI X IN RADIANTI

Tale messaggio informa l'utente che deve fornire il dato (ossia, il valore attuale di

x) necessario per l'esecuzione della successiva operazione di lettura. Ovviamente,

l'esecuzione non procede finchè tale dato non è stato fornito.

Esercizi

8.1. Dette A e B la base e l'altezza di un tnangolo, scrivere un programma che

legga i valori di A e B e stampi l'area del triangolo.

8.2. Se a, b e c indicano le lunghezze dei lati di un triangolo, la sua area può

essere calcolata con la formula

s = Vp(p - a) (p - b) (p - c)

nove p è il semiperimetro del triangolo.Scnvere un programma che, letti I valori di a, b e c calcoli e stampi il pen­

metro e l'area del triangolo.

8.3. Scrivere un programma che, dati i valori a, b ed n, calcoli e stampi il valore

b-a[ (b-a) J-6- f(a) + 2 f -2- + f(b)

READ ., A, N, B, NP, J

supponendo che i dati siano forniti in uno dei modi seguenti:

(a) 7.3, l O, - 3.5, 87, 1010

(b) 7.3, 10/

(c) 73., l, O., O, O

(d) - lO E - 3

737

S. E-S, 102, -3(e) + 7.03 E + 2, - 38, 5.5, lO

- 78

(O 1.1.1,2.2,2,3,8,15

8.6. Se zI = 1.1 + 3i, z2 = 5 + 8i e z3 = i sono tre numeri complessi, scrive­

re un programma che calcoli e stampi la loro somma ed i loro moduli.

8.7. Scrivere un programma che calcoli e stampi la somma ed il prodotto di due

numeri complessi assegnati.

8.8. Supponiamo che le istruzioni

REA L A, N

COMPLEX OMEGA

DOUBLE PRECISION B

READ.,A,N,OMEGA,B

facciano parte della stessa unità di programma. Indicare come devono essere

fomiti i dati perché dopo l'esecuzione della frase di lettura le variabili A.

N. OMEGA e B abbiano tutte valore zero.

Page 56: Fortran

9Scelte e decisioni

9.1. Controllo esplicito dell'esecuzione: l'istruzione GOTO-incondizionato

La sequenzialità del flusso di un algoritmo può essere interrotta in situazioni

che impongono la scelta tra blocchi di istruzioni alternativi in base al verificarsi

o meno di una determinata condizione. Queste situazioni di scelta vengono de­

scritte in FORTRAN mediante opportune istruzioni che sono l'argomento dei

prossimi paragrafi e che, insieme alle strutture di ripetizione che verranno presen­tate nel prossimo capitolo, permettono di controllare quasi completamente l'e­

secuzione di un programma. Esistono però situazioni che richiedono un controlloesplicito dell'esecuzione del programma. Tale controllo viene realizzato mediantel'istruzione GO TO-incondizionato.

Questa istruzione ha la forma seguente:

GOTOn

dove:

• GO TO è la parola chiave;• n è l'etichetta di una frase eseguibile che deve essere presente nella stessa unità

di programma cui appartiene l'istruzione GO TO-incondizionato.

L'esecuzione della frase GO TO n provoca il trasferimento del controllo della

esecuzione all'istruzione la cui etichetta coincide con n. Così, per esempio, l'ese­

cuzione delle istruzioni:

N=lGO TO io

9 N=N+lOO

lO J = N + 30

avviene nel modo seguente: si pone uguale ad uno il contenuto della cella N el'esecuzione prosegue poi, sequenzialmente, a partire dall'istruzione individuatadall'etichetta numero lO. L'istruzione intermedia N = N + 100 viene completa­mente ignorata.

I"

Page 57: Fortran

IO.

102 103

Esempio 9.1. Sia f(x) una funzione reale di variabile reale definita da:

Supponendo noto il valore di x si vuoI calcolare la Quantità v = f(x) + x2.

La situazione di scelta relativa a questo problema è la seguente:

dove c è un'espressione logica il cui valore. valutato al momento dell'esecuzione

dell'istruzione IF (c) THEN. determina la scelta tra i due blocchi di istruzioni.

L'effetto deIl'esecuzlOne di questa struttura è esattamente quello indicato in

fig. 9.1: se la condizione indicata dalla espressione c è vera vengono eseguite

le istruzioni del blocco l e sono ignorate quelle del blocco 2 mentre, se la condi­

zione c è falsa vengono eseguite soltanto le istruzioni del blocco 2. In entrambi

i casi l'esecuzione continua con l'istruzione che segue immediatamente END IF.

La struttura decisionale IF-THEN-ELSE è quindi caratterizzata da una frase

iniziale IF (c) THEN e da una frase finale END IF. La frase intermedia ELSE

serve ad evidenziare sia la fine del primo blocco di istruzioni che l'inizio del se­

condo. Il primo blocco, detto anche b!-occo_'I!1~~, è costituito da tutte le istru­

zioni che seguono IF(c) THEN e precedono ELSE mentre il secondo, detto

anche blocco ELSE:_' è costituito da tutte le istruzioni che seguono ELSE e pre-

'cedono END IF. Siosservi che, in quanto eseguibile, la frase ELSE può avere unall j

,',\ etichetta ma è proibito farvi riferimento mediante altre frasi di controllo. ;' i

per x ~ 1.5

per x < 1.5l x-l

f(x) = ~ OIF (c) THEN[blocco di istruzioni 1] +- (blocco THEN)

ELSE[blocco di istruzioni 2] +- (blocco ELSE)

END IF

E' importante osservare che l'istruzione GO TO-incondizionato deve essere

usata in modo opportuno: infatti un suo uso eccessivo e indiscriminato dà luogo

a programmi di difficile lettura e comprensione.

L'analisi fatta sugli algoritmi e la loro descrizione ha messo in evidenza la ne­

cessità di strutture che, in presenza di più blocchi di istruzioni alternativi. per­

mettano di sceglierne uno in base alla veridicità o meno di una particolare condi­

zione. In F77 è possibile tradurre una situazione di scelta tra due blocchi alterna­

tivi mediante il costrutto IF-THEN-ELSE. Un'analisi dettagliata di questo costrut­

to, non previsto nelle precedenti versioni del FORTRAN, facilita la comprensione

di un'altra istruzione che può essere usata in un processo decisionale e che è pre­

vista anche in F66: l'istruzione IF-logico.La generica situazione di scelta tra due blocchi di istruzioni alternativi può

essere schematizzata nel modo illustrato in fig. 9.1. Ad essa corrisponde la strut­

tura di controllo

9.2. Costrutto IF-THEN-ELSE

Bloccodiistruzioni

2

IF (X.GE.I.5) THENY=X-1.ELSEY=O.ENDIFY=Y+X .. 2

Figura 9.1. Scelta tra due blocchi di istruzioni.

Page 58: Fortran

104

Esempio 9.2. Siano x ed y due numeri dati e diversi da zero. Se x ~ y si cal­

colano le quantità s = x + y e p = xy, altrimenti si calcolano d = x - y e

q = d/(2 y).

Questa situazione può essere così descritta:

IF (X.GE.Y) THENS=X+YP=X.YELSED=X-YQ= D/(2. • Y)ENDIF

Si noti che è proibito trasferire il controllo dell'esecuzione di un programma

,·r dentro unblocco TH}:N oppure dentro u~-b/oc~~ ELSE~9uindi, ad esempio,

è sbagliato scrivere una successione di istruzioni come la seguente:

GO TO IO

IF (X. GE. Y) THEN

S=X+YlO Y=S.X

ELSE

A=X-YENDIF

Figura 9.2. Strutture decisionali mancantidel blocco TREN.

La struttura

IF (c) THEN

ELSE

[blocco di istruzioni]

ENDIF

corrisponde al diagramma di fig. 9.2 mentre

IF (c) THEN

[blocco di istruzioni]

ELSE

ENDIF

IOS

Figura 9.3. Strutture decisionali mancantidel blocco ELSE.

In queste istruzioni infatti la frase GO TO IO trasferisce il controllo dell'ese­

cuzione dentro un blocco THEN.

In altre parole si può dire che in F77 non è permesso «entrare», mediante una

frase di controllo, dentro una struttura di scelt,!;~~~IQQ~rmt2~Q «!!~çrr-e-12_da una.­

struttura di questo tipo mediante opportune istruzioni di controllo eventual!12~e

presenti in un blocco THEN o in un blocco ELSE. In una situazione di questo

genere viene allora a mancare l'ipotesi, che generalmente accompagna una struttu­

ra decisionale, e che consiste nel presupporre che, scelta la strada da seguire, l'e­

secuzione prosegua con l'istruzione successiva a quella finale della struttura stessa.

La presenza di una istruzione di controllo dentro una struttura decisionale può

quindi compromettere la leggibilità di un programma e la possibilità di seguirne

facilmente il flusso.

Una struttura decisionale deve prevedere anche situazioni in cui li/W dei dueblocchi THEN oppure ELSE è vuoto ovvero le situazioni rappresentate nelle

figu re segue nti:

corrisponde a quello di fig. 9.3. Quando il blocco ELSE è vuoto l'istruzione

ELSE può essere omessa. Si osservi che le situazioni rappresentate dalla fig. 9.3

sono equivalenti a quelle di fig. 9.2: basta esprimere in modo opportuno la con­

dizione che determina la scelta.

9.3. Strutture decisionali annidate

I blocchi di istruzioni che compaiono nella struttura lF-THEN-ELSE possono

a loro volta contenere altre strutture di scelta; è quindi possibile avere più costrut­

ti IF-THEN-ELSE uno dentro l'altro ciascuno dei quali deve essere chiuso da una

istruzione END IF. Situazioni di questo tipo vengono dette strutture annidatemtendendo per nido ael costrutto decisionale IF-THEN-ELSE tutte le istruzioni

comprese tra la frase iniziale lF (c) THEN e quella finale LNU IF.

Negli esempi seguenti. i nidi delle strutture di controllo sono stati evidenziatigraficamente mediante parentesi quadre

---j",---------------------~

Page 59: Fortran

106107

Esempio 9.3. La trascrizione in F77 delle istruzioni indicate in fig. 9.4 è la se­

guente:

Esempio 9.4. Dati i coefficienti reali a. b. c di una equazione di secondo grado

ax2 + bx + c == O si selezionano. mediante l'indicatore ind. diversi casi:

ind == - 2

ind == - I

ind == O

ind == I

significa che l'equazione è del tipo c == O:

significa che l'equazione è del tipo bx + c == O:

significa che l'equazione è del tipo ax 2 + bx + c == O ed ha radici reali;

significa che l'equazione è del tipo ax 2 + bx + c == O ed ha radici com­

pIesse coniugate.

In fig. 9.5 si riportano il diagramma di flusso e le relative istruzioni F77.

IF (A.EQ.O.) THENIF (B.EQ.O.) THEN

~IND =-2ELSEIND == -- lENDIFELSEDELTA==Bu2 -4.*A*CIF (DELTA.GE.O.O) THEN

[

IND = OELSEIND= lENDIFENDIF

Figura 9.5. Diagramma di flusso e istruzioni corrispondenti all'esempio 9.4.

Le parentesi quadre che accompagnano la lista delle istruzioni FORTRAN

negli esempi 9.3 e 9.4 servono soltanto a mettere in evidenza gli annidamenti di

più strutture IF-THEN-ELSE: esse non fanno certo parte del programma ma ne

facilitano la comprensione. E' possibile ottenere un risultato analogo incolonnan­

do le istruzioni relative ai nidi delle strutture di controllo più interne su posizioni

via via più spostate a destra; questo modo di incolonnare le istruzioni viene di

solito indicato con il termine inglese indentation (intaccatura, dentellatura) e

verrà utilizzato negli esempi che seguono~-Figura 9.4. Diagramma di flusso corrispondente all'esempio 9.3.

IF (J.LE.N) THENJ = N +JIF (X.GE.O.S) THEN

lS = X + TT =J. SELSES=X-TT = 3. * S ..2ENDIFT==T+XELSES==J*XIF (X.GT.O.O) THEN

[

T == SQRT(S)ELSET==-SENDIFX=T+SEND IF

, II

, i

Page 60: Fortran

Figura 9.6. Diagramma a blocchi e programma corrisponuente all'algoritmo deU'esempio 9.5.

Esempio 9.5. L'area di un triangolo i cui lati hanno lunghezze a, b, c è data dalla

formula di Erone s =vq dove q = p(p - a) (p - b) (p - c) con p = (a + b + c)/2.

Evidentemente tre valori a, b, c non rappresentano la lunghezza dei lati di un

triangolo reale se non sono positivi oppure se la quantità q non è positiva (esem­

pio a = l, b = 3, c = 5). Supponendo di avere più teme di valori di cui almeno

la prima costituita da valori positivi tali che q > 0, scrivere un programma che

permetta di calcolare e stampare il numero «tot» delle teme lette. il numero

«n» di triangoli reali e la loro area media. Il programma termina quando si legge

una tema i cui elementi non sono tutti positivi.

108

PROGRAM ARMEDIINTEGER TOTTOT =0N =0SOM =O.

IO READ •. A. B. CTOT = TOT + IIF (A.GT.O..AND.B.GT.O..AND.C.GT.O.) THEN

P = (A + B + Cl/2.Q = p .(P - A) • (P - Dj. (P - C)IF (Q.GTO.O) THEN

N =N + IS = SQRT(Q)

ELSES =0.

ENDIFSOM=SOM+SGOTO IO

ELSEAM= SOM/NPRINT •. ·SU'. TOT. 'TERNE DI VALORI'PRINT •. N. 'SONO LATI DI TRIANGOLI REALI'PRINT •. 'l"AREA MEDIAE" DATA DA!. AM

END IFSTOPEND

101 On O

SOI11 0

/

109

E' possibile risolvere questo problema con l'algoritmo seguente dove «sorn» in­

dica la somma delle aree dei triangoli e la doppia numerazione evidenzia le istru­

zioni interne alla struttura decisionale.

l. Poni tot = 0, n = O, som = O

2. leggi: a, b, c

3. incrementa di l il valore di tot4. se i tre valori letti sono positivi

allora: 4.1. calcola p = (a + b + c)/2 e q = p(p - a)(p - b)(p - c)

4.2. se q> Oallora: calcola s =vq, incrementa di l il valore di n

ed esegui 4.3.

altrimenti: poni s = Oed esegui 4.3.

4.3. aggiungi s a som

4.4. vai a 2.

altrimenti: esegui 5.

5. calcola l'area media am = sorn/n

6. scrivi: tot, n, am7. Stop

La lista del programma e il diagramma a blocchi sono dati in fig. Y.6.

Esempio 9.6. Scrivere un programma che risolva lo stesso problema dell'esem­

pio precedente prevedendo la possibilità. che, tra tutte le teme lette, nessuna rap­

presenti i lati di un triangolo reale: questo caso viene segnalato in fase di stampa

dei risultati.

Il problema può essere risolto mediante il seguente algoritmo:

l. Poni tot = O, n = O, som = O2. leggi: a, b, c

3. incrementa di l il valore di tot

4. se i tre valori letti sono positiviallora: 4.1. calcola p = (a + b + c)/2 e q = p(p - a)(p - b)(p - c)

4.2. se q> O allora: calcola s =~ incrementa di l il valore di n

ed esegui 4.:;

altrimenti: poni s = O ed esegui 4.3

4.3. aggiungi sa som

4.4. esegui 2.

altrimenti: se n> O allora: calcola am = som/n;scrivi: tot, n, am ;

esegui 5.

altrimenti: scrivi: tot ed esegui 5.

5. Stop.

~-----------

Page 61: Fortran

p---------------llO

La lista del programma è la seguente:

III

La lista del programma e il diagramma a blocchi sono i seguenti:

!1

PROGRAM ARMED2INTFGER TOTN=OSOM=0.0TOT=O

lO READ *, A, B, CTOT =TOT + IIF (A.GT.O..AND.B.GT.O..AND.C.GT.O.) THEN

P = (A + B + C)/2.Q = p * (P - A) * (P - B) * (P - C)IF (Q.GT.O.O) THEN

N=N + IS = SQRT (Q)

ELSES =0.0

END IFSOM =SOM +SGOTO IO

ELSE--IF (N.GT.O) THEN

AM = SOM/NPRINT *, 'SI SONO LETTE', TOT, 'TERNE DI VALORI'PRINT *, N, 'SONO RISULTATE LATI DI TRIANGOLI REALI'PRINT e , 'L"AREA MEDIA E" DATA DA:', AM

ELSEPRINT *, 'SI SONO LETTE', TOT, 'TERNE DI VALORI'PRINT *, 'NESSUNAINDIVIDUAUN TRIANGOLO REALE'

ENDIFENDIFSTOPEND

Esempio 9.7. Si vogliono ordinare tre valori dati a, b, c in modo che sia a ~ b ~ c.

Un algoritmo per risolvere questo problema è il seguente:

l. Leggi: a, b, c2. se a ~ b allora: esegui 3.

altnmenti: scambia a con b ed esegui 3.

3. se b ~ c allora: esegui 4.altrimenti: scambia b con c

se a ~ b allora: esegui 4.altrimenti: scambia a con b ed esegui 4.

4. scrivi: a. b, c5. stop.

PROGRAM ORDABCREAD *. A, B, CIF (ALE.B) THENELSE

S=AA=B8=S

END IFIF (B.LE.C) THENELSE

S=BB=CC=SIF (A.LE.B) THENELSE

S=AA=BB=S

END IFEND IFPRINT-. A, B, CSTOPEND

9.4. Strutture decisionali concatenate

Nella pratica si presentano spesso situazioni di scelta in cui intervengono più

condizioni che si escludono a vicenda ovvero situazioni che sono descritte da una

costruzione del tipo:

se: condizione 1 allora:esegui l'azione l

altrimenti se: condizione 2 allora:

esegui l'azione 2

altrimenti se: condizione n allora:

esegui l'azione naltrimenti: esegui l'azione n + 1.

Page 62: Fortran

112 113

Figura 9.7. Strutture decisionali concatenate.

se x < OseO~x~1

se x> l

x2

x(x - l)

x+2y = f(x) e f(x) =

IF (X.LT.O.O) THENY=X**2

ELSE IF (X.LE.l.O) THENY = X • (X - 1.0)

ELSEY=X +2

END IFS=Y+H

Le istruzioni seguenti:

Esempio 9.8. Dati i valori x ed h si vuoi determinare la quantità s = y + h dove

F

Blocco diistruzioni

n + l

Blocco diistruzioni

n

Blocco diistruzioni

2

Blocco diistruzioni

Tali processi decisionali, visualizzati in fig. 9.7, vengono descritti in F77 me­

diante la struttura:

IF (cl) THEN

[blocco di istruzioni l]ELSE IF (c 2 ) THEN

[blocco di istruzioni 2]

ELSE IF (cn

) THEN

[blocco di istruzioni n]

ELSE[blocco di istruzioni n + l]

END IF

dove cl' c2

' ..., cn

sono espressioni logiche che vengono valutate in sequenza

nell'ordine in cui esse compaiono; non appena una di esse risulta vera viene ese­guito il blocco di istruzioni che la segue mentre se nessuna espressione risulta

vera è eseguito il blocco di istruzioni che segue la frase ELSE.Si osservi che ogni blocco di istruzioni che segue una delle frasi lF (c l) THEN

oppure ELSE IF (Ci) THEN è implicitamente seguito da un trasferimento allafrase finale END IF della struttura. Risulta quindi importante l'ordine in cui com­paiono nella struttura decisionale le singole espressioni logiche in quanto. tra piùespressioni vere, è la prima quella che comanda l'esecuzione della struttura.

hanno l'effetto indicato in fig. 9.8: si valuta la prima espressione X.LT.O.O;

se essa risulta vera si pone Y uguale ad X ** 2 e l'esecuzione riprende dalla istru­zione che segue END IF ovvero S = Y + H (in questo caso avremo s = x2 + h).

Se invece la prima espressione risulta falsa si valuta la seconda ovvero si stabiliscese x è minore o uguale ad l. Nel caso in cui questo risulti vero si pone Y uguale ad

X * (X - l.) e l'esecuzione riprende con l'istruzione S = Y + H che in questo casoequivale a s = x(x - l) + h. Se nessuna delle due espressioni logiche precedentiè vera si pone Y uguale ad X + 2. e l'esecuzione continua ancora con S = Y + H

che in questo caso equivale a s = x + 2 + h.

y..-x+2

Figura 9.8. Diagramma di flusso relativo all'esempio 9.8.

Page 63: Fortran

114115

9.5. Riepilogo

Da quanto detto fino ad ora segue che una qualunque struttura decisionale

è aperta dalla istruzione

IF (c) THEN

e chiusa da

END IF

Tra queste due frasi possono comparire una o più istruzioni

IF (l.LE.O) THEN

N=OELSE IF (J.GT.IO) THEN

N=3ELSE IF (J.LE.S) THEN

N = lELSE

N=2ENDIF

ELSE IF (c) THEN

ELSE

ENDIF.

può essere sostituita dalla sola

PROGRAM ORDABC

READ -. A, B, CIF (A.GT.B) THEN

S=AA=BB = S

END IF

IF (B.GT.C) THENS=BB=CC=SIF (A.GT.B) THEN

S=AA=BB =S

END IFEND IFPRINT • A, B, CSTOPEND

permettono di calcolare correttamente il valore di N in quanto verrà eseguita

una sola frase di assegnazione, quella corrispondente alla prima espressione logica

che risulta vera; se tutte le espressioni sono false si esegue l'istruzione che segue lafrase ELSE.

Esempio 9.10. Il programma relativo all'esempio 9.7 può essere così modifi­cato:

se J < O

se 1 < J < 5se6<J<IO

se J > lO

N vale O

N vale 1N vale 2N vale 3

ELSE

ENDIF

che deve sempre seguire le eventuali ELSE IF presenti. Le frasi IF (c) THEN,

ELSE IF (c) THEN, ELSE sono seguite da blocchi di istruzioni la cui esecuzione

è subordinata alla veridicità delle espressioni logiche presenti nella struttura e che

possono a loro volta contenere altre strutture decisionali. Ogni blocco di istruzio­

ni che segue una delle frasi IF (c) THEN, ELSE IF (c) THEN, ELSE può essere

vuoto ovvero privo di istruzioni. Ricordiamo che se è vuoto il blocco che segue

la frase ELSE è possibile omettere l'istruzione ELSE stessa ovvero la successione

di istruzioni

ed al più una istruzione

Esempio 9.9. Sia N una variabile intera il cui valore deve essere determinato in

base a quello di un'altra variabile intera J secondo le regole seguenti:I!Il;

!Le istruzioni seguenti:

§!.empio 9.11. Dati tre valori reali a, b, c calcolare e stampare M = max (a b c)ed m = rnin (a, b, c) , ,

Page 64: Fortran

116

PROGRAM MAXMIlREAL MAX,MINREAD -. A, B, CIF (A.GT.B) THEN

MAX=AELSE

MAX=BEND IFIF (C.GT.MAX) THEN

MAX=CEND IFIF (A.GT.B) THEN

MIN = BELSE

MIN=AEND IFIF (C.LT.MIN) THEN

MIN=CEND IFPRINT *, 'MASSIMO .: MAX,'MINIMO =', MIN

END

Si osservi che, quando il blocco ELSE è vuoto, non si ottiene nessun migliora­

mento del programma dalla omissione della frase ELSE, anzi tale omissione può

rendere meno chiaro e leggibile il programma.

9.6. lf-logico: una struttura particolarmente semplice

Supponiamo di voler descrivere in FORTRAN una situazione nella quale unasola istruzione, che chiameremo istruzione dipendente, deve essere eseguita op­pure ignorata in base alla veridicità o meno di una condizione (cfr. fig. 9.9).

Il costruHo

IF (c) THENistruzione dipendenteELSEEND IF

produce l'effetto desiderato in quanto l'istruzione viene eseguita se (e soltanto

se) la condizione c risulta vera altrimenti essa viene ignorata.Questa situazione può essere scritta in modo più sintetico nella forma

IF (c) istruzione dipendente

117

F

Figura 9.9. Diagramma corrispondente alla istruzione If'-logìco.

alla quale si dà il nome di IF-Iogico. L'esecuzione di questa istruzione, presentesia in F77 che in F66, ha quindi l'effetto seguente: si valuta l'espressione logica c;se essa risulta vera viene eseguita l'istruzione dipendente altrimenti tale comandoviene ignorato. In ogni caso l'esecuzione continua con l'istruzione che segue l'IF­

logico.Sono esempi di istruzioni IF-Iogico i seguenti:

IF(J.NE.IO) SUM=O.IF (ABS(X - Y).LE.EPS) X = XI + SQRT (A + B)IF (X.GT.Y.OR.H.LE.l.E - 3) JMAX = 20

L'istruzione dipendente che accompagna un IF-Iogico non deve essere né un al- ,

tra IF-Iogico nè una delle seguenti istruzioni: IDO, IF (c) THEN, ELSE IF (c) THEN, ELSE, END IF, END. !

Esempio 9.12. Siano dati N valori della variabile A ciascuno dei quali è numeratomediante un numero progressivo I, l E;;; I E;;; N. Si vuoi calcolare quanti valori di

A sono maggiori di UfO.

Se indichiamo con NP il numero totale dei valori positivi di A il problema può

essere risolto dal programma seguente:

PROGRAM NPOSI~EAD *, NNP=O

100 READ *, l, AIF (A.GT.O.O) NP = NP + 1IF (I.EQ.N) STOPGO TO 100END

1-

Page 65: Fortran

II~Il:i

I(~

118

Si osservi che il valore di NP ovvero il numero dei valori positivi viene incre­

mentato di una unità se A> O; il controllo IF(I.EQ.N) viene invece eseguito sem­

pre qualunque sia il valore di A. 1\ programma termina, mediante l'esecuzione

della frase STOP, quando sono stati esaminati tutti i valori di A ovvero quando I

è uguale ad N; se I < N l'esecuzione prosegue con la lettura del successivo valore

di I e di A. Da notare che il programma non prevede la scrittura del valore finale

di NP; qualora essa venisse richiesta due azioni dovrebbero essere eseguite alla fine

della lettura dei dati: la scrittura del contenuto di NP e l'interruzione dell'esecu­

zione del programma. Tali comandi non possono essere realizzati mediante una

sola istruzione e quindi il programma scritto deve essere modificato, per esempio,

nel modo seguente:

PROGRAM NPOS2

READ *, N

NP=O100 READ *, I, A

IF (A.GT.O.) NP = NP + 1IF (I.NE.N) GO TO 100

PRINT *, NPSTOP

END

Questo esempio mette in evidenza che l'efficacia della frase di controllo IF..­

logico è ~~te~oim~~t~li~itata dal fatto che, quando risulta vera la condizione-in­

dicata nell'istruzione stessa, si può eseguire un solo comando: \'istruzione dipen­

dente. Per questo motivo, per realizzare senza il costrutto IF-THEN-ELSE una

situazione di scelta tra due blocchi alternativi di istruzioni, si deve utilizzare insie­

me all'IF-logico l'istruzione GOTO incondizionato. A questo proposito vediamo

come devono essere modificati alcuni degli esempi di questo capitolo senza far

uso del costrutto IF-THEN-ELSE.

Esempio 9.13. Le istruzioni dell'esempio 9.8 equivalgono a:

IF (X.LT.O.O) GO TO 100IF (X.LE.I.O) GO TO 200

Y = X + 2.GOTO 300

100 Y =X .. 2GO TO 300

200 Y = X * (X - 1.0)300 S =Y + H

r119

Esempio 9. J4. Un programma che serva a calcolare il massimo ed il minimo tra

'tre valori dati è il seguente (cfr. esempio 9.11):

PROGRAM MAXMI2REAL MAX, MINREAD *, A, B, CIF (A.GT.B) GO TO \O

MAX=BGOTO 20

\O MAX = A20 IF (C.GT.MAX) MAX = C

IF (A.GT.B) GO TO 30MIN=AGOT040

30 MIN = B40 IF (C.LT.MIN) MIN = C

PRINT *, 'MASSIMO =', MAX, 'MINIMO =', MINSTOPEND

Dagli esempi visti risulta chiaro che, non facendo uso della struttura decisio­

nale IF-THEN-ELSE, si scrivono programmi «meno facili» nel senso che la loro

comprensione è resa più difficoltosa dagli inevitabili «salti» di esecuzione.

Si osservi che il FORTRAN consente di evidenziare un punto di un programma

mediante l'istruzione costituita dalla sola parola chiave

CONTINUE

L'esecuzione di tale frase, di solito accompagnata da una etichetta, non ha altro

effetto se non quello di far proseguire sequenzialmente l'esecuzione del program­ma.

In mancanza del costrutto IF-THEN-ELSE è possibile realizzare la situazione di

scelta descritta in fig. 9.1 mediante le istruzioni IF-Iogico e CONTINUE nel modoseguente:

IF (c) GOTO Il)

[blocco di istruzioni 2]

GOTO n 2n) CONTINUE

[blocco di istruzioni I]

11 2 CONTINUE

Analogamente la situazione di fig. 9'.2 può essere realizzata nel modo seguente:

Page 66: Fortran

120

IF (c) GOTO n l

[blocco di istruzioni]

n l CONTINUE

9.7. GOTO-calcolato

Nei paragrafi precedenti si è visto come si può scegliere una tra più alternative

possibili in base al verificarsi di una condizione. Quando questa scelta è determi­

nata sulla base del valore di una espressione intera si può usare l'istruzione GOTO­

calcolato che in F77 ha la forma seguente:

GOTO (n l' n2, ... , nm) , espressione intera

dove:• GO TO è la parola chiave:

• n n n sono etichette non necessariamente distinte di frasi eseguibilil' 2"'" m

della stessa unità di programma cui appartiene il GOTO-calcolato;

• la virgola che precede l'espressione intera può essere omessa.Questa frase opera nel modo seguente: si calcola il valore k dell'espressione in­

tera; se l ~ k ~ m l'esecuzione prosegue con l'istruzione identificata dalla eti­

chetta nk

, altrimenti l'esecuzione prosegue con l'istruzione che segue il GOTO-

calcolato.In F66 l'espressione intera che compare in questa frase deve essere costituita

solo da un nome di variabile intera e non è prevista la virgola che la precede.

Inoltre in F66 non è specificato l'effetto della frase nel caso in cui il valore k

sia minore di l o maggiore di m.

Esempio 9.15. L'istruzione

GOTO (30, 40, SO), N + l - L

dà luogo ad un salto alla frase 30 se N + l - L vale l, alla frase 40 se N + l - L

vale 2, alla frase SO se N + l - L vale 3. Se il valore di N + l - L è minore di l

o maggiore di j l'esecuzione prosegue in modo sequenziale.

Esempio 9.16. L'istruzione

GOTO (7, lO, 15,7), M

provoca l'esecuzione dell'istruzione 7 se M vale 1 oppure 4, dell'istruzione lO

se M vale 2 e dell'istruzione 15 se M vale 3. Se M < l oppure M> 4 l'istruzione

GOTU-calcolato non provoca nessun salto di esecuzione.

L

121

9.8.IF-aritmetico

Questa frase ha la forma seguente:

IF (espressione aritmetica) n .. n2, n3

dove:• IF è la parola chiave:

• nl, n2, n3 sono etichette non necessariamente distinte di frasi eseguibili della

stessa unità di programma cui appartiene l'IF-aritmetico.

L'espressione aritmetica che compare in questa istruzione può essere di tipo

intero, reale o doppia precisione.

Sono quindi esempi di istruzioni IF-aritmetico i seguenti:

IF (A) 10,20,30IF (1- J) 5, 5, 3IF (8 •• 2 - 4.• A • C) 20, 60, 60IF(I+2.L)Bl,1l,Bl

L'istruzione IF-aritmetico permette di controllare l'esecuzione del programma

in base al valore dell'espressione aritmetica che vi è indicata: se il valore del­

l'espressione è negativo l'effetto dell'IF-aritmetico è lo stesso di un GOTO n l ;

se il valore dell'espressione è zero l'effetto è quello di GOTO n2 mentre se il va­

lore dell'espressione è positivo l'effetto coincide con quello di GOTO n3. L'istru­

zione IF-aritmetico può essere quindi rappresentata nel modo descritto dalla fig.

9.10.

Figura 9.10. Diagramma a blocchi corri­spondente alla istruzione IF-aritmetico.

Esercizi

9.1 Scrivere un programma che legga il valore di x e stam pi il valore s(x) dove

stx) è uguale a - l se x < O, uguale a zero se x = Oed uguale a + l se x> O.

Page 67: Fortran

9.9 Scrivere un programma che, dati n valori della variabile A, determini quantidi essi sono negativi, quanti positivi e quanti nulli.

9.10 Scrivere un programma che risolva lo stesso problema dell'esercizio prece­

dente usando come unico strumento decisionale l'istruzione IF-Iogico.

Individuare gli eventuali errori nelle seguenti istruzioni FORTRAN:

\ ,.1 (

123

GOTO IO

lF (A.GT.B) THEN

X=X+A.By = X +.5. A

ELSE

END IF

lF (A.GT.3.1) GO TO IO

IF (A.GT.B) THEN

X=X+A.BELSE

X=A+B

y = X + 0.5. A

ENDIF

lO

IO

d)

b)

SI

116

-5, \

r -l C

a) IF (N.LT.IO) 10,20,30

30 IF (A.GT.B) THEN

IO X=X+A.B

y = X + 0.5. A

ELSE

ENDIF

20 CONTINUE

c) IF (A.GT.B) THEN

X=X+A.B

IF (X.GT.I. 7) GO TO lOELSE

X=A+B

lO Y = X + 0.5 • AENDIF

IF (N .EQ.O) IF (M.EQ.3) GOTO 515

IF (N.EQ.O.AND.M.EQ.3) GOTO 515

IF (A.LT.B.AND.GT.C) STOP

IF (A.LT.B. OR.A.GT.C) STOP

IF (A.GT.3 ..AND.A.LE.2.) A = A + B

GO TO (20, 30, 40, 50), X + 1.5

Tema data RisultatolO, 15,27 0,093,93,93 3,387, 16,87 1,3

9.8

9.4 Leggere tre interi e confrontarli. Il programma deve stampare una coppia

di interi così definita: (O, O) se i tre numeri sono distinti; (3, 3) se i tre nu­

meri sono uguali; (i, j) se l'i-ma e j-rno numero sono uguali. Per esempio:

9.3 Scrivere un programma per leggere tre interi e scriverli in ordine decrescente.

Dati: a) I 2 3

b) l 3 2

c) 2 l 3

d) 2 3 I

e) 3 1 2

t) 3 2 1

9.2 Scrivere un programma che permetta di calcolare e stampare i tre valoris(x l), s(x 2) ed s(x 3) con s(x) definita nell'esercizio precedente e xl = - 2,x2 = - I, x3 = 3.

122

9.5 Scrivere un programma che legga le coordinate di tre punti nel piano: PI

=:

=: (xl' YI) , P2 =: (X 2' Y2 ) , P3 =: (X 3' Y3 ) e calcoli la distanza tra PI

e P2

e ladistanza tra PI e P3' Il programma deve stampare la maggiore tra le due di­stanze calcolate.

9.6 Scrivere un programma che, letti tre valori x, Y e z; permetta di verificare

se essi costituiscono le lunghezze dei tre lati di un triangolo ossia se sonopositivi e se:

X + Y> z, X + z > Y, Y + z > x.

11 risultato del programma e un numero intero uguale a:

O se x, y, z non sono lati di un triangolo;

se x, y, z sono lati di un triangolo isoscele;

2 se x, y, z sono lati di un triangolo rettangolo;

3 altrimenti.

9.7 Indicare gli eventuali errori nelle seguenti successioni di istruzioni:

Page 68: Fortran

lOCicli

10.1. Strutture di ripetizione

Nella stesura di un qualunque programma si presenta spesso la necessità di ese­

guire più volte un gruppo di istruzioni; d'altra parte è evidente l'utilità di costrut­

ti che, realizzando un procedimento ripetitivo, permettono di eseguire un certo

numero di volte, automaticamente, le stesse operazioni con dati diversi.

Esempio 10.1. Dato un cerchio di raggio r la lunghezza della circonferenza è

data da 211"r mentre l'area è data da 11"~. Per calcolare e stampare l'area e la lun­

ghezza della circonferenza di 15 cerchi si procede nel modo seguente:

1. Ripeti 15 volte

1.1. leggi: r

1.2. calcola e stampa l'area

1.3. calcola e stampa la lunghezza della circonferenza

2. Stop

Esempio 10.2. Per determinare il voto medio riportato da uno studente che ha

sostenuto m esami si può seguire il seguente algoritmo nel quale s indica la

somma dei voti riportati dallo studente

1. Leggi: m2. poni s = O3. ripeti m volte

3.1. leggi un voto

3.2. aggiungi ad s il voto letto4. se m = Oallora: scrivi che lo studente non ha sostenuto esami;

vai a 5.

altrimenti: calcola il voto medio v = s/m;stampa: m e v;

vai a 5.

5. stop.

Page 69: Fortran

126

Il diagramma a blocchi corrispondente a questo algoritmo è quello rappresen­tato in fig. 10.1.

Figura 10.1. Calcolo del voto medio riportato dI uno studente che hl sostenuto m esami (cfr.esempio 10.2).

Se vogliamo calcolare i voti medi riportati da N studenti, basterà ripetere Nvolte questo algoritmo leggendo ogni volta il numero degli esami sostenuti ed ivoti riportati da ciascuno studente (cfr. fig. 10.2).

Negli esempi precedenti come in alcuni degli algoritmi del cap. l, è presenteuna struttura ripetitiva che può essere così schematizzata:

Ripeti, un numero fissato di volte.L__blocco di istruzioni

127

Tale struttura (ciclo finito) sottintende l'utilizzazione di un contatore ovvero diuna variabile il cui valore, indicando il numero di ripetizioni fatte, controlla l'e­

secuzione della struttura e ne determina l'inizio e la fine. Essa viene realizzata in

ripeti N volte

Figura 10.2. Calcolo deUemedie dei voti riportati da N studenti ciascuno dei Qualiha sostenutom esami (cfr. esempio 10.2).

Page 70: Fortran

128

FORTRAN mediante una frase opportuna (istruzione DO) la cui esecuzione atti­

va appunto un ciclo che si esaurisce dopo un numero finito di ripetizioni.Prima di descrivere dettagliatamente la frase DO è opportuno ricordare che esi­

stono situazioni cicliche nelle quali si ripete l'esecuzione di determinate istruzioni

subordinatamente al verificarsi o meno di una specificata condizione. Tali strut­

ture, già evidenziate nel cap. l come cicli iterativi, non sono quindi controllate da

un contatore ma da una condizione in base alla quale viene stabilito se interrom­

pere o meno il ciclo. I cicli iterativi sono quindi caratterizzati dal fatto che un de­

terminato blocco di istruzioni (corpo) viene eseguito ripetutamente un numero

imprecisato di volte e possono essere genericamente schematizzati in questo

modo:

Ripeti, sotto il controllo di una condizione,

L_blocco di istruzioni

dove l'esecuzione del blocco di istruzioni modifica almeno una delle variabili

che intervengono nella condizione (cfr. esempio 1.5).La fig. 10.3 mostra alcuni tipi di strutture cicliche iterative. Il primo ciclo,

indicato con la lettera (A), è detto ciclo WHILE ed è caratterizzato dal fatto che,

se la condizione non risulta vera, esso non viene mai attivato nel senso che non

vengono eseguite le istruzioni che ne costituiscono il corpo. Il ciclo contras­segnato dalla lettera (B) è detto ciclo UNTIL e presenta invece la particolarità

che il suo corpo viene sicuramente eseguito almeno una volta. Questa differenza

tra le due strutture è determinata dalla posizione dell'operazione di controllo che

si trova nel ciclo WHILE prima del blocco di istruzioni mentre nel ciclo UNTIL

è posta dopo. Il terzo tipo di struttura, contrassegnato con la lettera (C), è carat-

129

te rizzato dal fatto di avere il corpo suddiviso in due blocchi di istruzioni posti

uno prima ed uno dopo l'operazione di controllo. Evidentemente in questo caso

le istruzioni del blocco posto prima del controllo verranno eseguite sicuramente

almeno una volta mentre quelle del blocco che si trova dopo saranno eseguite

soltanto se la condizione risulta falsa.Mentre alcuni linguaggi di programmazione, come ad esempio il PASCAL,

ed alcune estensioni del FORTRAN utilizzano istruzioni particolari per realiz­

zare i cicli WHILE e/o UNTIL, in F77 non è prevista alcuna istruzione di questo

tipo. E' però possibile definire un qualunque ciclo iterativo usando in modo op­

portuno le istruzioni IF-logico e GOTO-incondizionato. Così il ciclo WHILE

può essere descritto mediante il costrutto:

n1

IF (.NOT. condizione) GOTO n2[blocco di istruzioni]

GOTO n1

n2 CONTINUE

il ciclo UNTIL è equivalente alla sequenza di istruzioni:

n 1 CONTINUE

[blocco di istruzioni)

IF (.NOT.condizione) GOTO n1

mentre il ciclo (C) di fig. 10.3 può essere definito nel modo seguente:

n1

CONTINUE

[blocco di istruzioni l]

IF (condizione) GOTO n2[blocco di istruzioni 2]

GOTO n1n2 CONTINUE

E' opportuno sottolineare che occorre molta attenzione nell'uso dei cicli itera­

tivi come si può dedurre dall'esempio seguente.

Esempio 10.3. Si vuoi scrivere un programma che permetta di calcolare la radice

quadrata di un numero positivo x basandosi sul seguente procedimento:

lA)(8)

Figura 10.3. Alcune strutture cicliche iterative.

L

Page 71: Fortran

130

l. Dati due numeri positivi s e d tali che s2< x e d2> x2. poni m = (s + d)/2

3. se m2 = x allora: m è il risultato;scrivi m e vai a 4.

altrimenti: se m2 > x allora: poni d = m e torna a 2.

altrimenti: poni s = m e torna a 2.4. stop.

La fig. 10.4 rappresenta il diagramma a blocchi di questo procedimento nel

quale è presente un ciclo iterativo che sicuramente, per particolari valori di x

quali ad esempio x = 2. impone un numero infinito di ripetizioni. Questa situa­zione può presentarsi anche quando m = ...;; è rappresentabile con un numero

finito di cifre in quanto essa dipende dal criterio usato per controllare il ciclo.

A causa della precisione finita con cui si lavora sarà infatti difficilmente verificata

la condizione «se m2 = x» che determina la fine del procedimento. Per lo stesso

motivo sarà lecito accettare, come risultato, un valore il cui quadrato sia «quasi

uguale» ad x. tenendo presente che le richieste sulla «bontà» dell'approssimazione

non possono prescindere dalla precisione di macchina e dipendono dalle esigenze

di chi utilizza il programma. In base a queste considerazioni nel programma ripor­tato in fig. 10.5 viene utilizzata, quale criterio di arresto, la condizione «se

Figura 10.4. Diagrammi I blecchì che descrive il procedimento per il calcolo di V; x> O(esempi. 10.3). '

131

PROGRAM RADQ XREAD *. X. S. D. SIGMA

100 CONTINUEEMME = (S + D)/2.EMME2 = EMME" 2IF (ABS(EMME2 - X). LESIGMA) GOTO 200IF (EMME2.GT.x) THEN

D= EMMEELSE

S = EMMEENDIFGOTO 100

200 CONTINUEPRINT *. 'RISULTATovOTTENUTO', EMMEPRINT *, 'ERROREvCOMMESSO', ABS(EMME - SQRT(X))STOPEND

Figura 10.5. Diagramma a blocchi e programma F77 per il calcolo di .J;, x > O.

1 m2 - x I~ o» dove o è una quantità positiva maggiore della precisione di mac­china. Il valore di o viene acquisito in fase di lettura insieme a quello degli altri

dati del problema. Si osservi che un errore nella scelta della tolleranza o puògenerare ancora una ripetizione infinita delle istruzioni che costituiscono il corpodel ciclo. I criteri che vanno seguiti nella scelta di o esulano da un testo di questo

tipo e dipendono da considerazioni numeriche per le quali si rimanda, per esem­

pio, a [lO].

Le osservazioni fatte sull'esempio precedente mettono m evidenza una carat­teristica delle strutture cicliche iterative: esse sono semplici e di immediata com­

prensione ma nascondono il pericolo che, a causa di un errore logico nel pro­gramma o di un errore sui dati, la condizione che determina la fine del ciclo

non venga mai verificata. Per evitare questo inconveniente è opportuno fissare

un numero massimo di ripetizioni in modo che la situazione ripetitiva sia con­

trollata non solo dalla condizione presente nel ciclo ma anche da un contatore

che ne determina l'interruzione non appena sono state eseguite tutte le ripe­

tizioni. Il ciclo iterativo viene allora inserito in un ciclo finito dando luogo ad una

struttura che può essere così schematizzata:

Ripeti, un numero fissato di volte,: Ripeti, sotto il controllo di una condizione,

~ : blocco di istruzioni.&. __1__

Page 72: Fortran

137

Esempio 10.8. Dati n > Oe v scrivere un programma che permetta di calcolare

e stampare la quantità

Esempio 10.7. Scrivere un programma che, dati i numeri interi n, a ed r permette

di calcolare e stampare ogni elemento della progressione aritmetica di ragione

r definito da:

I

I

ijJ.1

IIIII

II

I

k = O, l, ... , nuk = a + kr

PROGRAM UOUKINTEGER A,K,R,N,UKREAD., A, R, NDO 100 K =O.NUK = A +K. RPRINT ., K, '- MOvELEMENTO', UK

100 CONTINUESTOPEND

Si osservi che il ciclo presente in questo programma è costituito da N + l ripe­

tizione del rango e che la variabile del DO è usata più volte nelle istruzioni del

rango.

n

q = Uo+ u1 + ... + un = L Ukk=O

dove Uo= v e uk

= k(k + l) uk _ l per l ..;;k ..;; n.

Un algoritmo per risolvere questo problema è il seguente:

l. Leggi: n e v

2. poni Uo = v3. poni q = v

4. ripeti n volte per k = l, 2.... , n4.1 calcola uk = k(k + i) Uo4.2 poni q = q + uk

4.3 poni Uo = uk

5. scrivi: q6. stop

)/

Infine va tenuto presente che è proibito trasferire il controllo dell'eSeCuzione. ti! dentro al rango di un DO da un punto al di fuori del rango stesso ovvero non è Ttj}-

consentito «entrare» nel rango di un DO se non attraverso l'istruzione iniziale /TDO che definisce e controlla il ciclo stesso.

r

PROGRAM VOTMEDINTEGER VOTOREAD.,MS=O.O00 27 I = l,M,

READ .,VOTOS =S +VOTO

27 CONTINUEIF (M.NE.O)THEN

VM =S/MPRINT., 'VOTOvMEDIOvSUvM =', M, 'vESAMI', VM

ELSEPRINT -. 'LOVSTUDENTEvNONvHAvSOSTENUTOvESAMI'

ENDIFSTOPEND

Esempio 10.6. Il programma seguente permette di calcolare e stampare il votomedio riportato da uno studente che ha sostenuto M esami (cfr. esempio 10.2 efig. 10.1).

Si osservi che l'istruzione DO che compare in questo programma equivale a

DO 27, I = l, M, l. L'esecuzione del ciclo inizia ponendo uguale ad l il valoredella variabile I; si calcola quindi il numero di ripetizioni imposte dal DO: se lostudente non ha sostenuto alcun esame (M = O) si ha C = O, il rango del DO viene

ignorato e l'esecuzione prosegue con l'istruzione che segue 27 CONTINUE; seinvece lo studente ha sostenuto uno o più esami vengono eseguite M volte le i­

struzioni del rango ed alla fine del ciclo S contiene la somma ,!ei votLtiPortati

~Q~!!!~nt~m~n!!"e I ~~_~valo~~~±~~ .

136

Alcune regole da seguire

Affinché una struttura ripetitiva controllata dall'istruzione DO possa essere

correttamente eseguita è necessario che non si creino situazioni che impediscono

l'esecuzione sequenziale dei passi mediante i quali si realizza il ciclo-DO.~l'~~-

(9 ticolare, la variabile del DO non de~~ mai essere ridefinJ!~4!ntro il rango~~o--essa può essere usata in una qualunque istruzione del rango purché non

venga modificato il suo valore ", ~l!.Qltre, l'istruzione finale di un ciclo-DO nondeve essere un'altra istruzione DO nè un'istruzione GOTO-inco~dizioJlilto,

GOTO-assegnato, IF-aritmetico, IF(c) THEN, ELSE, ELSE IF(c) THEN, END IF,

RETURN, STOP, END. L'istruzione che viene comunemente usata come fraseterminale di un DO è l'istruzione CONTINUE che, avendo come unico effettoquello di far proseguire l'esecuzione uet programma, permette di evidenziare il

rango del DO senza intervenire operativamente nel ciclo.

Page 73: Fortran

138 139

ovvero:

Esempio 10.10. Scrivere un programma che, dato n ~ 5, permetta di calcolaree stampare le seguenti quantità:

DOlO I=I,NIF (I.LT.S) GOTO IOK = K + (I - 1)/2.L=L+2.1

IO M=M+I

DO IO 1= l, NIF (I.LT.5) GOTO 20K = K + (I - 1)/2.L=L+2.1

20 M =M + IIO CONTINUE

n

k = L (i - 1)/2i = 5

n

L 2i,i= 5

ti,i= I

m=

PROGRAM MLKINTEGER M, L, N, 1REAL KREAD., NM=OL=OK=O.ODO IO 1= l,N

M=M+IIF (I.LT.S) GO TO IOK = K + (I - 1)/2.L=L+2.1

IO CONTINUEPRINT., M, L, KSTOPEND

L'istruzione DO 10 I = l, N implica N ripetizioni del rango nel quale viene piùvolte utilizzata la variabile del DO. La prima istruzione del rango, M = M + I,

viene eseguita ad ogni ripetizione del rango mentre le frasi di assegnazione cheseguono l'IF-logico vengono eseguite soltanto se I ~ 5: durante le prime quattro

ripetizioni del rango risulta infatti vera la relazione I.LT.5 e l'esecuzione dell'istru­zione dipendente GOTO lO provoca un salto all'istruzione finale IO CONTINUE.Lo stesso risultato del programma precedente sarebbe stato ottenuto utilizzandouno qualunque dei seguenti cicli:

READ., NM=2.N+1S = 1.0DO IO I = l, M, 2S = S.I

IO CONTINUEPRINT., 'PRODOTTOvDElvPRIMI', N + l, 'vNUMERlvNATURALlvDlSPARI', SS =0.0DO IS 1=2,M,2S = S + 1

IS CONTINUEPRINT., 'SOMMAvDElvPRIMI', N, 'vNUMERlvNATURALlvPARI', SSTOPEND

In questo programma compaiono due cicli-DO i cui ranghi sono separati nelsenso che il secondo ciclo diventa attivo soltanto quando è terminato il primo;questo ha permesso di usare lo stesso nome di variabile I nelle due istruzioni DOsenza che si creino errori o ambiguità nell'esecuzione dei due cicli. Infatti, durantel'esecuzione del ciclo controllato dall'istruzione DO lO I = l, N, 21a variabile Iassume tutti i valori dispari compresi tra l ed N secondo le regole che comandanol'esecuzione di un ciclo-DO; al momento della disattivazione del ciclo l contieneil valore N + 2 e, con l'esecuzione della frase DO 15 I = 2, N, 2 la variabile I

viene ridefinita ed il suo valore posto uguale a 2. Durante questo ciclo la variabilel assume tutti i valori pari compresi tra 2 ed N - 1 e vale N + 1 quando il ciclo

termina.

Esempio 10.9. Dato un intero positivo dispari M = 2N + I il programma se­guente calcola il prodotto dei primi N + l numeri interi positivi dispari e la som­

ma dei primi N numeri interi positivi pari.

Basandosi su questo algoritmo si ha:

PROGRAM SOMUKREAD.,N,VUo=vQ=VDO 20, K= l,N

UK = UO. K. (K + I)Q=Q+UKUO=UK

20 CONTINUEPRINT., QSTOPEND

Si osservi che gli elementi uk

vengono calcolati usando l'aritmetica reale per evi­

tare fenomeni di overflow nel calcolo di k(k + I) con aritmetica intera.

i

!]il

Page 74: Fortran

140 141

Figura 10.8. Diagramma a blocchi relativo al problema dell'esempio 10.11.

Sarebbe stato però notevolmente diverso scrivere:

DOlO 1=I,NM=M +1IF (LLT.5) GOTO lOK = K + (I - 1)/2.

lO L=L+2*1

In questo caso infatti, quando I è minore di S, l'istruzione dipendente

GOTO lO impone un salto all'istruzione finale del DO che, essendo la frase di

assegnazione L = L + 2 * I, provoca la modificazione del contenuto della variabilen

L la quale, alla fine del ciclo, contiene il valore ~ 2i e non quello richiesto dalio; l

problema.

10.4. Cicli e strutture decisionali

In molti problemi l'attivazione di un ciclo-DO può essere subordinata al veri­ficarsi o meno di una certa condizione.

Esempio 10.11. Dato un intero n> O scrivere un programma che permetta di cal­colare la quantità m definita da:

n

m= [ (i+1)n se n è parii= l

n

m= [ 2in se n è disparii= l

Il programma richiesto deve realizzare il seguente procedimento:

l. Leggi: nn

2. se n è pari allora: calcola m = ~ (i + 1) n e vai a 3.i= l

naltrimenti: calcola m = ~ 2 i n e vai a 3.

io; l

3. scrivi: m

4. stop.

READ -. NEMME =0.0IF (N/2 * 2.EQ.N) THEN

DO 150 I = l, NEMME = EMME + (I + 1.0) * N

150 CONTINUEELSE

DO 200 I = l, NEMME = EMME + 2. * I * N

200 CONTINUEENDIFPRINT *,'N =', N, 'vM =', EMMESTOPEND

F v

J

Una descrizione più dettagliata di questo algoritmo (cfr. fig. 10.8) mette in

evidenza la necessità di usare due strutture cicliche alternative la cui attivazioneè determinata dalla condizione «se n è pari».

Facendo uso della struttura decisionale IF-THEN-ELSE possiamo quindi scn­vere il programma seguente:

E' importante osservare che quando un ciclo-DO fa parte del blocco di istru­zioni che seguono una delle frasi IF (c) THEN, ELSE IF (c) THEN, ELSE, il

rango del DO deve essere interamente contenuto nel blocco che contiene la fraseiniziale del ciclo ossia l'lstruzione DO.

Page 75: Fortran

-_...:---'/;(

142

D'altra parte, se /'istruzione IF (c) THEN compare dentro il rango di un ci­

c/o-DO anche la corrispondente istruzione END IF deve far parte del rango.

Esempio 10.12. Supponendo di aver intervistato N pers~ne di se.sso diverso s~

vuoI calcolare l'età media dei maschi e quella delle femmine. I dati sono raccolti

in N schede ciascuna delle quali contiene l'età ed un codice che indica il sesso del-

l'intervistato (O per le femmine ed I per i maschi). .Indichiamo con Nm (NO il numero totale dei maschi (delle femmine) e con

Em (ED la somma delle loro età; il problema può essere allora risolto come segue:

I. Leggi: N

2. poni Nm = Oed Nf = O

3. poni Em = Oed Ef = O

4. ripeti N volte:

4.1. leggi una coppia di dati

4.2. se codice = 1 allora: aggiungi una unità ad Nm eaggiungi l'età ad Em. Vai a 4.3.

altrimenti: aggiungi una unità ad Nf e

aggiungi l'età ad Ef. Vai a 4.3.

4.3. continua il procedimento ripetitivo5. calcola e stampa l'età media dei maschi e quella delle femmine

6. stop.

11 programma richiesto può essere allora il seguente:PROGRAM ETAMEDINTEGER CODICE,ANNIREAD -. NNM=ONF=OEM =0.0EF =0.0DO 151 NUM= l,NREAD *, ANNI,CODICEIF (CODlCE.EQ.1) THEN

NM=NM+IEM =EM + ANNI

ELSENF = NF + 1EF =EF + ANNI

END IF151 CONTINUE

ETAM = EM/NMETAF = EF/NF ,PRINT * 'NUMERO'lDEI'lMASCHI', NM,''lETA'' MEDIA, ETAMPRINT *: 'NUMERO'lDELLE'lFEMMINE', NF, 'v ETA" MEDIA', ETAFSTOPEND

143

10.5. Trasferimento ad istruzioni fuori del rango

La ripetizione delle operazioni indicate dalle istruzioni del rango di un DO può

essere interrotta trasferendo il controllo dell'esecuzione dall'interno del rango ad

una istruzione che, pUT facendo parte della stessa unità di programma. non appar­

tiene al rango. In questo caso la variabile del DO mantiene, al momento dell'uscitadal ciclo, il valore definito durante l'ultima ripetizione.

Esempio 10.13. Dato N, si vogliono leggere al più N valori della variahile PESO;

la lettura dei dati deve terminare con il primo valore negativo o nullo della va­riabile. Scrivere un programma che segnali se tutti gli N valori di PESO sono po­sitivi e, in ogni caso, fornisca il numero di valori letti.

Seguendo lo schema indicato in fig. 10.9 si ha:

READ *, NDOIO,K=I,N

READ *, PESOIF (PESO.LE.O.O) GO TO 25

IO CONTINUEPRINT *, 'TUTTIvI vVALORIvSONOvPOSITIVI'K=N

25 PRINT *, 'NUMEROvDlvVALORIvLETTI', KSTOPEND

Figura 10.9.

Page 76: Fortran

144

Dopo aver acquisito il valore di N inizia il ciclo controllato dall'istruzioneDO l O, K = l, N; essa impone N ripetizioni del rango che è costituito da dueoperazioni: una di lettura ed una di controllo. Se tutti i valori della variabilePESO risultano positivi l'istruzione dipendente GOTO 2S non viene mai ese­guita ed il ciclo si esaurisce dopo N ripetizioni del rango. L'esecuzione prosegue

allora in modo sequenziale con l'istruzione che segue la frase terminale del DO.Siccome il ciclo è stato completamente eseguito, al momento della sua disattiva­

zione la variabile K contiene il valore N + l: da qui la necessità di inserire l'istru­

zione K = N prima della stampa del numero di dati letti. Nel caso in cui i valoridella variabile PESO non siano tutti positivi il ciclo viene interrotto non appena

si trova un valore negativo o nullo: in questo caso infatti l'esecuzione dell'istru­

zione dipendente GOTO 2S impone un salto nell'esecuzione al di fuori del rango

del DO che provoca l'immediata disattivazione del ciclo e l'esecuzione dell'istru­

zione individuata dalla etichetta 2S. Siccome il ciclo non è stato completato il

valore di K è quello definito durante l'ultima ripetizione e fornisce quindi il nu­

mero di valori letti: i primi K - l sono tutti positivi mentre il K-mo, essendo nega­

tivo o nullo, ha provocato l'interruzione delle operazioni di lettura.

Esempio 10.14. Il seguente programma permette di calcolare la radice quadratadi un numero positivo x mediante l'algoritmo UI fig. 10.6: \

PROGRAM RADICEREAD -. X, SIGMA, N, S, DDO 100 1= 1, N

EMME= (S + D)/2.EMME2 = EMME •• 2IF (ABS(EMME2 - X).LE.SIGMA) GOTO 200IF (EMME2.GT.x) THEN

D=EMMEELSE

S= EMMEEND IF

100 CONTINUEPRINT., 'E" STATOvESEGUITOvILvNUMEROVMASSlMOvDl',

• 'vRlPETIZI0NI'STOP

200 PRINT., 'SONOVSTATEvESEGUITE,I, 'vRIPETIZI0N(PRlNT .,'E" STATOvTROVATOvlLvRISULTATO', EMMEPRINT., 'CONvUNvERRORE: ABS (EMME - SQRT(X»STOPEND

145

10.6. Cicli-DO annidati

Come mostra il diagramma di fig. 10.2, possono presentarsi situazioni che preve­dono due o più cicli finiti uno dentro l'altro (annidati). Il linguaggio F77 prevede

la possibilità di a.ttivare, all'interno del.ran...g..o di u. n.. DO.. '. altri Cicli-D.O. con. l'.unica */:­limitazione che il Jl111KiLdeldçJQ l!i'1 interno deve essere interamente contenutodentro al rango'del ciclo più esterno. V~ì~'~-p-~na--èii osservare 'che~ slc~~~;~~

vanabiI~~DO ~~;:;d~~ ~ai essere ridefinita dalle istruzioni del rango, le

istruzi~!.QQEhe _(;~!!!roll~I!.Q.gçti.fif1iti annidati devono usare variabili di nome - .~/,<!ive!S.-2' Non sono previste limitazioni sul numero di cicli-DO che possono essereannidati.

Esempio 10.15. Il seguente programma permette di calcolare e stampare il votomedio di N studenti (cfr. fig. 10.2):

PROGRAM MEDIE1INTEGER VOTOREAD., ND030 NS= l,N

PRINT -. 'STUDENTEvNUMERO', NSREAD .,MS=O.ODO 15 1= 1, M

READ., VOTOS=S+VOTO

15 CONTINUEIF (M.NE.O) THEN

VM = S/MPRINT., 'VOTOvMEDlOvSUvM =', M, 'v ESAMI', VM

ELSEPRINT -. 'LOvSTUDENTEvNONvHAvSOSTENUTOvESAMI'

END IF30 CONTINUE

STOPEND

Più strutture cicliche annidate possono utilizzare la stessa frase terminaI=. che,

in questo'caso, deve essere considerata come appartenente soltanto al rango ~e~

DO più interno.

Esempio 10.16. La successione di istruzioni:

N=ODO 50 M = 1,5K=MDO 50 J = O, 3

L= J50 N = N + l

Page 77: Fortran

146

equivale alla seguente:

N=ODO 100 M=I,5K=MDO SO J = O, 3L=J

SO N =N + l100 CONTINUE

Dopo l'esecuzione la variabile M vale 6, K vale 5, J vale 4, L vale 3 ed N vale20. Il rango del DO più interno, controllato dalla variabile J, viene ripetuto

20 volte mentre quello del DO più esterno che utilizza la variabile M, viene ese­

guito 5 volte.Anche se è previsto che due o più cicli-DO annidati si chiudano sulla stessa

frase può essere utile evidenziare il rango di ciascun ciclo mediante istruzioni

CONTINUE distinte.

Esempio 10.17. La successione di istruzioni:

N=OL=ODO lO 1=1,2

N=N+ lDO lO J=I,3

K=J + NDO lO M = 1,3

lO L=L+K

equivale alla seguente:

N=OL=ODO lO I = 1,2

N=N+ lDO 20 J = 1,3

K=J +NDO 30 M = 1,3

L=L+K30 CONTINUE20 CONTINUElO CONTINUE

Il rango del DO più esterno, controllato dalla variabile I viene eseguito 2 volte;

quello del DO intermedio, controllato da J, viene eseguito 6 volte mentre quello

del DO più interno, controllato dalla variabile M, viene eseguito 18 volte. Dopo

l'esecuzione delle istruzioni indicate le variabili I, J ed M contengono rispettiva­mente i valori 3, 4 e 4 mentre N contiene il valore 2, K il valore 5 ed L il valore 63.

..• _-----------

147

L'abitudine di separare i ranghi di cicli-DO annidati mediante istruzioni finali

distinte non è utile soltanto per aumentare la leggibilità di un programma ma 'ianche per evitare errori quando nel rango di uno dei cicli annidati vengono esegui- "te operazioni di controllo. Tali operazioni non devono infatti prevedere un tra- '

sferimento ad una istruzione che appartenga al rango di altri cicli interni; in parti­

colare è sbagliato trasferire il controllo dell'esecuzione del rango di un DO allafrase finale di un'altro ciclo in esso annidato.

Esempio 10.18. Il seguente gruppo di istruzioni

L=ODO lO M = 1,5

L=L+MIF (M.LE.3) GOTO lODO 20 K = 1,3

20 L = L + (M - K)IO CONTINUE

corrisponde al diagramma a blocchi di fig. 10.10; il rango del DO più esterno,

controllato dalla variabile M, viene eseguito cinque volte mentre il ciclo più in­terno viene attivato soltanto se M è maggiore di 3. Alla fine dell'esecuzione deidue cicli i contenuti delle variabili M, L e K sono rispettivamente 6, 4 e 30. La

distinzione mediante etichette diverse delle frasi terminali dei due cicli è neces-

ripeti per m = 1,2,3,4,5

v

Figura 10.1O. I cicli finiti annidati esaminati nell'esempio 10.18.

Page 78: Fortran

148 149

10.3 Indicare gli eventuali errori nei seguenti gruppi di istruzioni:

c) DO lO K = l, lO

L=KIF (K.GT.5) GOTO lOL = K + 3 l''{ U

lO IF (L.LE.LM) K = L - 2

d) GO TO 5

DO lO I = l, 100

5 H = 0.5. I

A=I·H+AlO CONTINUE

saria per effettuare in modo corretto il trasferimento previsto nel rango del DO

più esterno. Sarebbe stato infatti sbagliato scrivere, per esempio, la successione di

istruzioni:

L=ODO lO M=1,5

L=L+MIF (M.LE.3) GOTO lODO lO K=I,3

lO L=L+(M-K)

in quanto l'istruzione dipendente GOTO lO trasferisce il controllo dell'esecu­

zione alla frase finale del ciclo più interno.

a) DO lO 1M1 = 1, 5

IMI = IMI + 3

lO CONTINUE

b) DO 5 K = N + 1, J, L5 IF(K.LE.MAN) IS = N • K

l'I V

\ .

Esercizi

10.1 Alcune delle istruzioni seguenti sono sbagliate. Perché?

10.2 Determinare il numero di ripetizioni del rango per ognuna delle seguenti

istruzioni:

DO 22 l = 22, 77, - 1DO 37 \JM-l= 1, 10,2 SCk (16

DO N, 1= 1, 10,2 rlODO lO, K = L - 3, J + 2, 3 - LI

DO 1 JS = 0.0, 8.0, 0.5 l'IO

DO 3 S = 0.0, 8.0, 0.5

DO 83 K = L + M, KDO 5 M = L, lO, LDO 21, ITER = LO, A + B,:,1.l

\

! l

f) DO lO l = 20, l, - l

Al = 1./2.

DO 20 K = l, l i I (lO L=K+3

20 CONTINUE

(a) DO lO l = 1,4 (b) S = O.S = O. DO lO l = 1,4S=S+I S=S+I

lO CONTINUE lO CONTINUE I

(c) S = O. (d) S = l.DO lO l = 4, l, - 1 DO lO l = 1,4S = S + 1./1 S = S • l

lO CONTINUE lO CONTINUE

e) IF (A - B.LE.E) THEN

DO lO I = l, N

X=X+HPRINT., X •• 2

ELSE

X=X-H

PRINT.,2. X

lO CONTINUE

END IF

10.4 Indicare il contenuto della variabile S dopo l'esecuzione delle sequenze diistruzioni (a), (b), (c), e (d) seguenti:

10.5 Scrivere un programma che, assegnate n ~ l teme di numeri interi, esegua

per ciascuna di esse quanto previsto nell'esercizio 9.4.

10.6 Scrivere un programma che, assegnate n ~ l teme di numeri reali, permetta

di stabilire per ciascuna di esse se i valori letti costituiscono i lati di untriangolo (cfr. esercizio 9.6).ì

c:

DO 3, 1= 8, 8DO 7 M = 1, 55, 1ODO lO J = lO, O, - 1 (f

DO 2, L = O,30 I

DO 6 K = 0.1, 3.5, 2.1

Page 79: Fortran

150

10.7 Scrivere un programma che, assegnato un numero intero positiv~ N, s~am~i. l h 2 r ~ N < 2r + l e le cifre della rappresentazione binariaIl valore r ta e c e ...."di N. (cfr. §3.l).

10.8 Scrivere un programma che permetta di stampare il valore che un polinomion .

. ., d -- l () - 1: a Xl assume per x = z asse-.a coefficienti reah di gra o n? 'Pn X - j= O i

gnato (l dati del problema sono: n, z ed i coefficienti ao' al' ..., an)·

[IlLe variabili dimensionate

11.1. Introduzione

Nel corso dei precedenti capitoli si è sempre associato un nome simbolico aduna singola locazione di memoria. In FORTRAN è possibile anche individuare

con un nome simbolico un insieme ordinato di locazioni consecutive atte a con­tenere dati tutti del medesimo tipo. Un tale insieme viene detto variabile dimen­siona!a (array) e le locazioni che lo costituiscono sono dette elementi della varia­bile dimensionata; ogni elemento può essere individuato specificandone in modo

opportuno la posizione tramite degli indici. In pratica, è possibile tradurre in

FORTRAN la notazione vettoriale comunemente usata, ad esempio, nella descri­zione di molti problemi e algoritmi di natura scientifica; tale possibilità si rivelatalvolta indispensabile per il trattamento di insiemi di valori omogenei.

Esempio Il. ( Consideriamo l'algoritmo descritto nell'esempio 10.8. In tale algo­

ritmo si fa uso della notazione vettoriale che permette una descrizione sintetica e

compatta delle operazioni da svolgere. In particolare al passo 4.1 si descrive il cal­

colo di uk ' ossia di u 1 se k = l, u2 se k = 2, e così via; i nomi uO

' u1

' ... un siriferiscono a entità fra loro distinte. Nel programma SOMUK non si fa corrispon­

dere una cella di memoria ad ognuno dei valori ul' ... , un' in quanto il nomesimbolico UK identifica sempre la stessa cella dove, al variare di K durante l'ese­cuzione del ciclo-DO, viene memorizzato ogni volta un valore diverso.

Supponiamo ora di voler scrivere un programma che, calcolati uO

' u1' ..., un'

stampi la somma degli elementi di posto dispari ul. u

3... e quella degli elementi

di posto pari uO' u2 ' ..• Se il valore di n è fissato, ad esempio n = 7, si può otte­nere lo scopo desiderato con il seguente programma:

Page 80: Fortran

152

READ., VUO=VUl = 2.• UOU2 = 2.• 3.• UlU3 = 3.• 4 .• U2U4 = 4.• S.• U3US = 5.• 6.• U4U6 = 6.• 7.• USU7 = 7.• 8.• U6SP = UO + U2 + U4 + U6SD= Ul + U3 + US + U7PRINT. 'SOMMA DEGU ELEMENTI DI POSTO PARI =', SPPRINT.: 'SOMMA DEGU ELEMENTI DI POSTO DISPARI =', SD

STOPEND

E' evidente che per valori grandi di n è molto scomodo scrivere un programma

analogo al precedente. Utilizzando invece una variabile dimensionata i cui ele­

menti contengano i valori uO

' u1' ... , un è possibile scrivere un programma che

risolve il problema qualunque sia n (cfr. esempio 11.10).

Esempio 11.2. Sono noti i voti conseguiti da 200 studenti di un corso di laurea

che prevede 30 esami. Per poter facilmente trattare questo insieme di dati si può

costruire una tabella rettangolare A di 200 colonne e 30 righe: in ogni colonna

si riportano i voti conseguiti da uno studente. La tabella A risulta così costituita

da 6000 dati: il voto conseguito dal j-esimo studente all'i-esimo esame si trova

all'incrocio fra la j-esima colonna e l'i-esima riga; esso è quindi individuato dalla

coppia di indici (i, j) e può essere indicato con il simbolo aj,j'

Nel seguito useremo il termine vettore per indicare un insieme di dati ognuno

dei quali è individuato da un solo indice (cfr. esempio 11.1) e il termine ma~ric~per indicare un insieme di dati ognuno dei quali è individuato da una coppia, di

indici (cfr. esempio 11.2). Un vettore è una tabella unidimensionale e una matnce

è una tabella bidimensionale; si possono costruire anche tabelle a tre o più dimen­

sioni, per poter trattare insiemi di dati particolari quali, ad esempio, il numero di

persone che abitano ad ogni piano ad ogni numero civico di ogni strada in una cit~ta, oppure i valori che una funzione di tre o più variabili assume su un reticolo di

punti. Ad una tabella, intesa come insieme di dati individuabili tramite indici,

si può far corrispondere in FORTRAN una variabile dimensionata.

153

Il.2. Nomi di variabili dimensionate e istruzione DIMENSION

Perché un nome simbolico possa essere considerato in una unità di programma

come nome di una variabile dimensionata, occorre che di ciò sia informato il com-~nj!atore:>al quale devono essere fomite, in particolar~-,-i;seg~~~ti indica;~~i:

• il tipo della variabile, ossia il tipo comune a tutti i suoi elementi; -

• il numero di dimensioni;• l'ampiezza di ogni dimensione.

Ad esempio, se si vuoi definire una variabile dimensionata corrispondente ad

una matrice di 30 righe e 200 colonne con elementi reali, si deve specificare

al compilatore che la variabile è di tipo reale e che ha due dimensioni, la prima di

ampiezza 30 e la seconda di ampiezza 200.

Le indicazioni suddette, insieme ad altre che verranno esaminate in seguito,

devono essere specificate tramite un dichiaratore di variabiledimensionata che ha

la forma:

dove:

• v è un nome simbolico che costituisce il nome della variabile dimensionata; iltipo della variabile è il tipo (esplicito o implicito) di v;

• n è il numero di dimensioni, e deve essere minore o uguale di 7 (in F66 deve

essere n ~ 3);

• dI" .. , dn sono i dichiaratori di dimensione. Per ogni valore di i, d ha la formaI

infj : SUPj

dove infj e SUPj sono la limitazione inferiore e la limitazione superiore per l'i­

esima dimensione. ~~~e ch~ v ha dimensioni costanti quando, per ogni i, inf. '" _. . . l

e SUPj sOIl~ espresslOnl aritmetiche ottenute combinando costanti e nomi di'oca-

stanti inte~~L~tre forme per infj e sUPi' consentite soltanto all'interno di sotto­programmi, verranno esaminate nel cap. 15. In ogni caso il valore di sup. deve

essere maggiore o uguale di quello di infj; se infj è uguale a l, il dichiaratore d.

può assumere la forma (unica consentita in F66) I

suP;

L'ampiezza dell'i-esima dimensione è data da

Sj = sUPi - infj + l

e l'ampiezza di v, ossia il numero totale dei suoi elementi, è il prodotto delle. n

ampiezze s., ovvero è data da n s..I i=l I

Page 81: Fortran

154

Esempio JJ.3. Nel dichiaratore di variabile dimensionata

T

155

Esempio 11.6. Le frasi

A (IO, 20)

si ha: n = 2, infl

= inf2 = l, sUPI = lO, sUP2 = 20; l'ampiezza della prima dimen­

sione è quindi s = lO, quella della seconda è s2 = 20, da cui segue che l'ampiezza

della variabile 1è SI x s2 = 200. Osserviamo che il dichiaratore usato è equiva-

lente ad uno qualunque dei seguenti:

A(I : 10,20) A(I : lO, l : 20) A(lO, l : 20)

PARAMETER (N = IO)REAL A(N, N + I), V(N), U(N)

definiscono la matrice reale A di lO righe e Il colonne e i vettori reali V ed U di

ampiezza lO. Notiamo che nei dichiaratori di dimensione compare il nome sim­

bolico N che non è un nome di variabile, bensì un nome di costante definito nella

precedente frase PARAMETER. Le due istruzioni sono pertanto equivalentialla frase

Nel seguito useremo abitualmente, per le variabili a una e due dimensioni,

la terminologia seguente: «vettore di lunghezza SI» in luogo di «variabile a una

dimensione di ampiezza SI»; «matrice di SI righe e s2 colonne», o «matrice

s x s », in luogo di «variabile a due dimensioni di ampiezze rispettive SI e s2 »;l 2 . .. b

«matrice quadrata di ordine n» in luogo di «variabile a due dimensioni entram e

di ampiezza n». Il significato di altre locuzioni usate in luogo delle precedenti

sarà facilmente deducibile da queste.

Un dichiaratore di variabile dimensionata può comparire in una frase dichia­

rativa di tipo, come negli esempi che seguono:

Esempio JJ.4. La frase

INTEGER N, M(60), VOTI (15,20)

indica al compilatore che N, M, VOTI sono variabili di tipo intero, e le ultime due

sono variabili dimensionate. In particolare M è un vettore di 60 elementi e VOTI

è una matrice di 15 righe e 20 colonne.

Esempio JJ.5. La frase

REAL L(lO), A(- 5 : 4), U(O : 20), Z(l : 5, 6), W(l, 3,4)

specifica che L, A, U, Z, W sono variabili dimensionate di tipo reale; in particolare

L è un vettore di lO - l + l = IO elementi;

A è un vettore di 4 - (- 5) + l = lO elementi;

U è un vettore di 20 - O + l = 11 elementi;

Z è una matrice di 5 - l + l = 4 righe e 6 - l + l = 6 colonne;

W è una variabile a tre dimensioni di ampiezze rispettive:

2 - l + l = l, 3 - l + l = 3 e 4 - l + l = 4.Osserviamo che L ed A hanno la stessa ampiezza, pur essendo diversi i loro dichia-

ratori di dimensione.

REAL A(lO, Il), V(lO), U(lO)

L'istruzione DIMENSION

Se si vuoI dichiarare che uno o più nomi sim bolici sono nomi di variabile di­

mensionata si può usare l'istruzione dichiarativa DIMENSION, la cui forma ge­nerale è:

DIMENSION lista

dove:

• DIMENSION è la parola chiave che identifica la frase;

• lista è una lista di dichiaratori di variabile dimensionata.

La presenza di un dichiaratore di variabile dimensionata in una frase DIMENSION

non ha alcun effetto riguardo al tipo della variabile stessa. A tal proposito occorre

osservare che una frase DIMENSION può precedere o seguire eventuali frasi di

specificazione di tipo in cui compaiano nomi di variabili dimensionate da essa

dichiarate. In ogni caso un dichiaratore di variabile dimensionata non può compa­rire in più frasi dichiarative nella stessa unità di programma.

Esempio 11. 7. L'istruzione

REAL MAT (5, io. O : l)

è equivalente a una qualunque delle coppie di istruzioni seguenti:

REAL MATDIMENSION MAT(5, IO, O: 2)

DIMENSION MAT(5, IO, O: 2)REAL MAT

E' invece sbagliata la presenza nella stessa unità di programma delle due istru­zioni seguenti:

Page 82: Fortran

l:

156

REAL MAT (5, lO, O: 2)DIMENSION MAT (5,10, O: 2)

Va notato che spesso si preferisce evitare l'uso dell'istruzione DIMENSION

e inserire i dichiaratori delle variabili dimensionate in frasi di specificazione di \ I

tipo; si veda a tale proposito quanto è stato detto nel cap. 5 circa l'opportunità !di dichiarare esplicitamente il tipo di tutte le variabili in ogni unità di program­

ma.

11.3. Nomi di elementi di variabile dimensionata

Un elemento di variabile dimensionata è identificato da un nome della forma

dove:

• v è il nome della variabile dimensionata;

• n è uguale al numero delle dimensioni di v;

• e l , . · . , en sono espressioni intere, dette espressioni indice, che possono conte­

nere a loro volta riferimenti a elementi di variabile dimensionata (anche di v stes­

sa). In F66 le espressioni indice potevano avere soltanto una delle forme seguenti

j * s + k, j * s, s ± k, s, k

dove j e k sono costanti intere, e s è una variabile intera.Il simbolo (el' ... ,en) è detto indice dell'elemento; nel seguito useremo tal­

volta il termine «inuice» in luogo di «espressione indice» quando non vi sia ambi­guità.

Esempio 11.8. Date le variabili dimensionate IPIV, A, Z, W dichiarate con la frase

DIMENSION IPIV (IO), A(5, 6), Z(lO, IO, lO), W(O : lO)

sono sin tatticamente corretti i seguenti nomi di elementi:

IPIV (IO)IPIV (3. J)IPIV (IPIV(I)A(I, J)A(I •• 2,1)A(I, IPIV(K»Z(I + 2, I + 1,5)W(K)W(I+(J-I).N)

157

Sono invece sbagliati i nomi A(I) e IPIV(X): il primo perché contiene una sola

espressione indice mentre A è una variabile a due dimensioni, il secondo perché

X è un'espressione che non può essere usata come espressione indice. ( r • ',. I "/,. 7 Il

Il nome di un elemento di variabile dimensionata può essere usato come unnome di variabile ordinaria in una espressione. nella lista di una frase di ingres­so/uscita, e in una frase di assegnazione alla sinistra del segno =. Occorre co­

munque tener presente che, al momento dell'esecuzione dell'istruzione in cui

esso compare, il valore di ogni espressione indice deve essere compreso fra lalimitazione inferiore e la limitazione superiore della dimensione corrispondente.Così nell'esempio 11.8, i riferimenti a W(K) ed A(I, J) sono corretti soltanto

se è O~ K ~ lO, l ~ I ~ 5 e I ~ J ~ 6.

Esempio 11.9. Date le variabili IND e A dichiarate con la frase

INTEGER IND (5), A(O : 5,6)

supponiamo di eseguire le seguenti istruzioni

DO 15 1=1,5IND (I) = I +1PRINT., A(lND(I), I - l)

15 CONTINUE

Mentre la prima istruzione del rango del DO viene sempre eseguita correttamente,

la seconda provoca una situazione di errore per I = l e 1= 5. Infatti per I = l la

seconda espressione indice I - l, assume il valore zero che non è compreso fra le

limitazioni inferiore e superiore della seconda dimensione di A. Analogamente,

per I = 5 la prima espressione indice IND(I) ha il valore non consentito 6.

Esempio 11.10. Si vuole scrivere un programma che, da ti n >O e v, permetta di

calcolare uk = k(k + l) uk _ l' per k = l, ... , n con Uo= v. Si vuole inoltre cal­

colare e stampare la somma dei valori uk con k dispari e quella dei valori uk con

k pari (cfr. esempio 11.1).

Per poter specificare l'ampiezza della variabile dimensionata U i cui elementi

contengono i valori uo' ul' ... , un occorre fissare una limitazione superiore per n.Il seguente programma, SOMUKV, risolve il problema per n ~ 50.

Page 83: Fortran

158 159

TBAMB contiene il numero di bambini, maschi e femmine. nati negli anni dal

1980 al 1985.

Nel programma ora scritto è evidente l'utilità di poter usare per la matrice

TOT indici di riga e di colonna variabili rispettivamente fra O e I e fra 1980 e

1985. Se infatti avessimo usato il dichiaratore, consentito anche in F66,

TOT (2, 6)

PARAMETER (LINF = 1980, LSUP = 1985)INTEGER TOT (0:1, LINF : LSUP), SEX, ANNO, NOK, TBAMBREA D -. N

C AZZERAMENTO DEI TOTALINOK=OTBAMB =0DO 100 ANNO = LINF, LSUPDO 100 SEX = 0,1TOT (SEX, ANNO) = O

100 CONTINUEC CICLO: SI LEGGE UNA COPPIA DI DATI PER VOLTA.C SE NON E' VALIDA SI PROCEDE ALLAC LETTURA SUCCESSIVA,C ALTRIMENTI SI AGGIORNA NOK, E EVENTUALMENTE,C TBAMB E TOT (SEX, ANNO)

DO 200 I = l, NREAD -. SEX, ANNOIF (SEX.NE.O.AND.SEX.NE.l) GOTO 200NOK= NOK + lIF (ANNO.LT.LINF.OR.ANNO.GT.LSUP) GOTO 200TBAMB = TBAMB + lTOT (SEX, ANNO) = TOT (SEX, ANNO) + l

200 CONTINUEC STAMPA DEI TOTALI

PRINT ., 'NUMERO DI COPPIE VALIDE:'. NOKIF (NQ!<..NE.O) THEN

PRINT., 'TOTALE BAMBINI NATI FRA IL', LSUP,':', TBAMBPRINT ., ..... MASCHI .....

DO 300 ANNO = L1NF, LSUPPRINT -. •ANNO', ANNO, ':', TOT (O, ANNO)

300 CONTINUEPRINT ., '.... FEMMINE .....

DO 400 ANNO = L1NF, LSUPPRINT ., •ANNO', ANNO, ': TOT (l, ANNO)

400 CONTINUEELSEENDIFSTOPEND

Osserviamo che per evitare riferimenti a elementi U(K) con K > 50 si è inserito

nel programma un controllo sul dato in ingresso N; se N > 50 il programma ter­mina subito con un messaggio di avvertimento.

PROGRAM SOMUKVPARAMETER (NMAX = 50)DlMENSION U(O : NMAX)READ., N, VIF (N.GT.NMAX) GOTO 50

C CALCOLO DI U(K), K = O, l, ... , NU(O) = VDO 25 K = l, NU(K) = U(K - l) • K • (K + l)CONTINUE

CALCOLO DELLA SOMMA DEGLI U(K), CON K DISPARISD=O.0035K= I,N,2SD = SD + U(K)CONTINUE

CALCOLO DELLA SOMMA DEGLI U(K), CON K PARISP= O.00 45 K = O, N, 2SP = SP + U(K)

45 CONTINUEC STAMPA DEI RISULTATI

PRINT ., 'SD =', SD, 'SP =', SPSTOP

50 CONTINUEPRINT., 'N DATO TROPPO GRANDE: NMAX =', NMAXSTOPEND

Esempio 11.11. Si vuoI sapere quanti bambini sono nati negli anni dal 1980 al1985 in una comunità costituita da N persone; si vuole inoltre costruire una ta­

bella da cui risulti quanti fra i bambini suddetti sono maschi e quanti femmine.Il programma seguente risolve il problema. A tale scopo si legge, per ogni per­

sona appartenente alla comunità, una coppia di dati costituita da: sesso (codi­

ficato come O se maschio e l se femmina) ed anno di nascita. I totali desiderativengono memorizzati nella matrice TOT di due righe, una per ogni sesso, e sei co­lonne, una per ogni anno dal 1980 al 1985: gli indici di riga possono assumere i va­lori O e l, e gli indici di colonna variano fra 1980 e 1985. Osserviamo che, per ga­

rantire la corretta esecuzione del programma, si controlla ogni coppia di dati cheviene letta: una coppia non è considerata valida se il suo primo elemento non èzero oppure uno. Al termine dell'esecuzione del ciclo controllato dall'istruzione

DO 200 I = l, N la variabile NOK contiene il numero di coppie di dati valide e

25C

·1 35i ~i':

C

Page 84: Fortran

160 161

in cui si mettono in evidenza soltanto il numero di righe e il numero di colonne,

avremmo dovuto far variare gli indici di riga fra 1 e 2 e quelli di colonna fra 1 e 6;

così, in corrispondenza alla coppia di dati SEX e ANNO avremmo dovuto far

riferimento all'elemento

TOT (SEX + 1, ANNO - LINF + 1)

anziché, come si è fatto, all'elemento

Esempio 11.12. Siano dati i vettori di ampiezza s = IO

INTEGER LISTA uo), COPIA (- 5 : 4)

11 primo elemento di LISTA è LISTA (1), il secondo è LISTA (2), e così via

fino al decimo che è LISTA (l O); invece, nel vettore COPIA la prima posizione

spetta all'elemento COPIA (- 5), la seconda a COPIA (- 4), e la decima e ultimaa COPIA (4).

TOT (SEX, ANNO).

\J ~ [> I ~ I \/1 ~ Ivi 1'/" ( / i '

IlA. Disposizione in memoria degli elementi di una variabile dimensionata

Ad ogni elemento di una variabile dimensionata di ampiezza s corrisponde un

numero fra l ed s che rappresenta la sua posizione in memoria all'interno del­l'insieme di locazioni consecutive identificato dal nome della variabile. La posi­

zione di un elemento dipende dal numero di dimensioni della variabile, dai valori

delle espressioni indice e dai dichiaratori di dimensione, secondo lo schema ri­

portato in fig. Il.1, dove il simbolo i" indica il valore della k-esima espressione

indice e".

Dalla fig. Il.1 si deduce anche che ~~E1atrici sono «memorizzate per colonne»,

in quanto in memoria tutti gli elementi della-'pri~~-cofonna,ordinati per valorr

crescenti dell'indice di riga, precedono gli elementi della seconda colonna, ordinati

allo stesso modo, e così fino all'ultima colonna.

In generale, gli elementi di una variabile di n dimensioni sono ordinati nel modo

seguente: l'n-esimo indice In varia da infn a sUPn; per ogni varore di in l'indice

in_ 1 varia da infn_ 1 a sUPn_l; per ogni coppia di valori di in e in_ 1 l'indice

in- 2 varia da infn_ 2 a sUPn_2; così via fino a il che varia da infl a sUPI per ogni

insieme di valori di in' in_I' ... , i2 .

Esempio 11.13. Le matrici A e 8 dichiarate con la frase

Figura Il.1. Ordinamento degli elementi di variabile dimensionata.

DlMENSION H(2, 2, 2)

DIMENSION A(2, 3), 8(3,2)

hanno ambedue ampiezza 6. A ha due righe e tre colonne e i suoi elementi sono

ordinati nel modo descritto in fig. I l.2; 8 ha tre righe e due colonne ed è memo­

rizzata per colonne come si vede in fig. Il.2.

L'ordinamento degli elementi della variabile dichiarata da

è infine descritto in fig. 11.3, da CUI si vede che tutti gli elementi il cui terzo

indice i3

vale 1 precedono tutti quelli per i quali i3 vale 2, ossia che H è «rnemo­

rizzata per piani».

In fig. IlA si visualizza tramite le frecce l'ordine in cui sono memorizza ti gli

elementi di A, 8 e H; in questa figura si evidenzia la memorizzazione per colonne

di A e 8 e per piani di H.

Lo schema riportato in fig. Il.1 è valido per n ~ 3 anche in F66. A questo pro­

posito osserviamo che secondo tale versione del FORTRAN è consentito che il

valore di una espressione indice nel nome di un elemento di variabile dimensionata

superi la limitazione superiore della corrispondente dimensione, purchè la posizio­

ne dell'elemento, calcolata secondo lo schema di fig. Il.1 ,non superi l'ampiezza

totale della variabile; così, per esempio, se le dimensioni della matrice MAT sono

specificate dalla frase

posizione

l + (il - infl)l + (il - infl) + (i2 - inf2) * SI

l + (il - infl) + (i2 - inf2) * SI++ (i3 - inf3) * SI * s2

l + (il - infl) + (i2 - inf2) * SI++ (i 3 - inf3) * SI * s2 + ...... + (in - infn) * SI * s2 * ... * sn- I

-,

IIIIII

I

:

elemento

v (il)

v (il' i2)v (il' i 2, i3)

dichiaratore divariabiledimensionata

v (di)

v (di' d2)v (di' d2, d3)

Dalla figura si deduce, in particolare, che gli elementi di un vettore sono dispo-sti in memoria nell'ordine crescente degli indici. . - - ------ - '

Page 85: Fortran

I",

162

Figura Il.3. Memorizzazione conseguente alla frase DIMENSION H(2 ,2,2).PROGRAM POLXCALCOLO DEL VALORE DI UN POLINOMIO DI GRADO N.LE.lOPARAMETER (NMAX = lO)DIMENSION A(O: NMAX)LETTURA DI NREAD *, NIF (N.LE.NMAX) THENLETTURA DEI COEFFICIENTI E DI X

DO IO 1= O,NREAD -. A(I)

CONTINUEREAD -. X

CALCOLO ESTAMPA DEL VALORE DEL POLINOMIOPOL = A(N)D020 I=N-I,O,-I

POL = POL * X + A(I)CONTINUEPRINT -. 'X =', X, 'POL(X) =', POL

ELSEIL VALORE DI N E' TROPPO GRANDEL'ESECUZIONE TERMINA CON LA STAMPA DI UN MESSAGGIO

PRINT *, 'N TROPPO GRANDE. NMAX =', NMAXENDIFSTOPEND

lO

20

n

p (x) = \"' a. xin L 1

i=O

per un assegnato valore ai x.

Il seguente programma si basa sull'identità

Pn(x) = «(anx + an_l) x + an_z)x + ... + al) x + ao'coefficienti del polinomio ao' ... , an sono memorizzati nel vettore A, mentre

il valore richiesto è memorizzato nella variabile PO L.

163

dei programmi. In assenza di controlli, una tale situazione non viene segnalata nel

momento in CUI si verifica e può condurre ad un risultato sbagliato o alla conclu­

sione forzata dell'esecuzione del programma. Così, data la matrice MAT sopra

specificata, per effetto del riferimento a MAT (6,5) si andrebbe ad operare sulla

ventiseiesima locazione di memoria a partire da quella in cui è memorizzato

MAT (I, I), ossia su una locazione che non fa parte della memoria riservata a

MAT.

Nell'esempio seguente, come già si è fatto nell'esempio 10.10, si effettua un

controllo sui dati in ingresso per evitare il riferimento a elementi di un vettore

la cui posizione superi l'ampiezza del vettore stesso.

c

C

Esempio 11.14. Calcolo del valore di un polinomio di grado n ~ IO a coefficienti

reali

C

C

CC

65432

IA(l,I) A(2,1) A(l,2) A(2,2) A(l,3) A(2,3)

B(l,l ) B(2,1) B(3,1) B(l,2) B(2,2) B(3,2)

Elemento

Posizione

Elemento

B(l,I) B(I,2)

A(l ,1~A(l ,2/A(l ,3) BJ0J2lt ~ t ~ t

A(2,1) A(2,2) A(2,3) B(3,1) B(3,2)

D1MENSIONA(2, 3) D1MENSION B(3,2)

H(lì:~ H(l,2,2)

tH(2,1,2) H(2,2,2)

H(l,I,I) H(l,2,1)

~ -: ~H(2,1,I) H(2,2,IV

D1MENSION H(2,2,2)

Elemento

Posizione

Figura 11.2. Memorizzazione conseguente alla frase DIMENSION A(2,3), B(3,2).

INTEGER MAT (5, 5)

Figura Il.4. Memorizzazione delle variabili dimensionate A, B, H.

un riferimento all'elemento MAT (6, I) è sbagliato in F77, ma non in F66

in quanto la sua posizione è 6 < 25; il nome di elemento MAT (6,5) è invece

sbagliato anche in F66, in quanto ad esso corrisponderebbe la posizione 26 > 25.

Si noti che, nella pratica, un controllo diretto ad evitare che in fase di esecu­

zione si verifichino situazioni non consentite del tipo ora esemplificato, comporta

u.n costo molto elevato in termini di tempo-macchina; per questo motivo la mag­

gior parte dei compilatori lo attiva soltanto dietro esplicita richiesta del program­

matore. Di solito è buona regola far attivare il controllo in fase di messa a punto

I'I\

.\\

I\ !

l

Li".I!;1

l

Page 86: Fortran

1M 165

Esempio 11.17. Il seguente programma H l O calcola e stampa gli elementi di una

matrice reale H quadrata di ordine lO; gli elementi hi,j con i, j = l, ... , n sono

definiti da:

Dagli esempi ora svolti è evidente che l'utilizzo del nome di una variabile di­

n2ensioÌÙlta senza indici in una frase di lettura obbliga a fornire i dati nell'ordinein cui gli elementi sono disposti in memoria; analogamente, se lo si usa in una

frase di uscita, l'ordine in cui i contenuti degli elementi verranno stampati è quello

.p.r~stabi~~~~J!,el~boratore. In molte situazioni è utile poter stabilire un ordinediverso di ingresso o di uscita dei dati; nel cap. 13 si descriveranno tutte le possi­

bilità previste in F77 per il trattamento delle variabili dimensionate nelle opera­

zioni di ingresso/uscita.Consideriamo ora alcuni esempi di programmi che utilizzano variabili dimensionate.

11.5. Esempi di utilizzazione delle variabili dimensionate

Volendo scrivere dei programmi in cui si usano variabili dimensionate si pone il

problema di come poterle leggere e/o stampare. Nei paragrafi precedenti si è vistoche una lista di ingresso/uscita può contenere nomi di elementi di variabili di­

! mensionate; d'altra parte in FORTRAN è consentito usare in una lista di ingres- I

1, J so/uscita il nome di una variabile dimensionata al posto della lista esplicita dei INl nomi di tutti i suoi elementi nell'ordine in cui figurano in memoria. j

Esempio 11.15. Dato il vettore

INTEGER V(7)

l'istruzione

PRINT ., V

significa che si devono stampare i contenuti Gei 7 elementi di V nell'ordine in

cui compaiono in memoria; in altri termini essa equivale a

PRINT., V(l), V(2), V(3), V(4), V(5), V(6), V(7)

h . -l,j

i + ji,j = l, ... , n.

Analogamente, si equivalgono le due trasi seguenti:

READ., VREAD -, V(l), V(2), V(3), V(4), V(5), V(6), V(7)

Esempio 11.16. Data la matrice

INTEGER A(2, 3)

l'istruzione

READ., A

indica che si devono leggere 6 dati interi e che il primo verrà memonzzato inA(l, l), il secondo in A(2, 1), e così via (cfr. fig. 11.2); la frase è quindi equiva-

lente a

READ., A(l,l), A(2,1), A(l,2), A(2,2), A(l,3), A(2,3)

L'istruzione

READ., A(l,1), A(l,2), A(l,3), A(2,1), A(2,2), A(2,3)

indica invece che si devono leggere tutti gli elementi di A, ma per righe anziché

per colonne. e non è quindi equivalente alle due precedenti.Supponendo ad esempio di voler leggere e memorizzare in A la matrice

2

5le prime due istruzioni di lettura impongono di fornire i dati nell'ordine

l 4 2 5 3 6,mentre la terza impone l'ordine seguente

l 2 3 4 5 6.

PROGRAM HlODlMENSION H(lO, lO)DO lO J = l, lODOlO 1=1,10H(I, J) = 1./(I + J)PRINT*, H(I, J)

lO CONTINUESTOPEND

Consideriamo ora il seguente programma HN:

PROGRAM HNPARAMETER(NM = lO)DIMENSION H(NM, NM)READ -. NDOlO J=I,NDO lO I = l, NH(I, J) = 1./ (I + J)PRINT *, H(I, J)

lO CONTINUESTOPEND

Se in ingresso è N = IO, il programma HN calcola gli stessi valori di HlU, men­

tre se in ingresso è N < lO, tale programma assegna un valore soltanto ad

alcuni degli elementi della variabile H la cui ampiezza è uguale a 100.

Così, se è N = 5, viene definito il contenuto degli elementi corrispondenti alle

posizioni da l a 5, da 11 a 15, da 21 a 25, da 31 a 35, da 41 a 45, mentre non

viene assegnato alcun valore a tutti gli altri elementi.

~-------------_.

Page 87: Fortran

•167

10

Zj = L ai,j yj i = l, ... , lOj=l

Si osservi che le operazioni di ingresso/uscita in ORDVET riguardano un sot­

toinsieme dei 20 elementi di X, e non si è quindi potuto usare la frase READ -. X

oppure PRINT *. X.

e DO lO 1 = 1,80010 1=1,8

Esempio Il.19. Data una matrice quadrata A di ordine lO ed un vettore y di IO

elementi, il seguente programma PRaD l O calcola e stampa il vettore prodotto

z = Ay; gli elementi di z sono definiti da

PROGRAM PRODIOREAL A(IO, IO), Y(IO), Z(IO)

C LETTURA DELLA MATRICE (PER COLONNE) E DEL VETTORE YREAD *, AREAD -. Y

C CALCOLO DEL VETTORE PRODOTTO ZDOlO 1=1,10Z(I) = O.DOlO J=I,10Z(I) = Z(I) + A(I, J) * Y(J)

lO CONTINUEC STAMPA DEI DATI E DEI RISULTATI

PRINT *, 'MATRICE DATA, PER COLONNE'PRINT *, APRINT *, 'vETTORE DATO v'PRINT -. YPRINT *, 'VETTORE PRODOTTO'PRINT *, ZSTOPEND

dove ai,j sono gli elementi di A e Yj quelli di y.

Osserviamo che in questo caso la dimensione del problema, ossia la dimensione

dei vettori e delle matrici interessate, è fissata a priori e non costituisce un dato.

Ciò consente di usare i nomi delle variabili dimensionate, senza indici, nelle frasidi ingresso/uscita.

E' interessante notare che PRaD l O può essere usato soltanto per problemi di

dimensione n = IO; se si vuole utilizzarlo, ad esempio, per n = 8, si deve sosti­tuire la costante 8 alla costante lO nella frase REAL e sostituire le frasi

00101=1,10 e 0010 1=1.10

rispettivamente con le frasi

Esempio Il.18. L'algoritmo seguente permette di ordinare in senso crescente n

numeri reali dati Xl'···' Xn '

1. Leggi: n, xl' X2' , x n

2. Scrivi: xl' X2' , x n

3. Per i = I. ..., n - I

3.1. Poni min = i

3.2.Perj=i+ l, ... ,n3.2.1. Se xj < xmin : poni min = j e vai a 3.2.2;

altrimenti: vai a 3.2.2;

3.2.2. Continua il ciclo controllato da j

3.3. Se min > i: scambia xmin con xi e vai a 3.4

altrimenti: vai a 3.4

3.4. Continua il ciclo controllato da i

4. Scrivi: xl' X2' ... , x n

5. Stop

Supponendo n ~ 20, l'algoritmo viene realizzato dal seguente programma:

PROGRAM ORDVETD1MENSION X(20)

C LETTURA DEI DATI. SI SUPPONE N.LE.20READ *, NDOlO 1=I,NREAD *, X(I)

IO CONTINUEPRINT -. 'VETTORE DATO'DOl5 I=I,NPRINT *, X(I)

15 CONTINUEC RIORDINAMENTO DEGLI ELEMENTI DI X

DO 50 I = l, N - IMIN=IDO 45 J = I + I, NIF (X(J).LT.X(MIN)) MIN = J

4S CONTINUEIF (MIN.GT.I) THEN

TEMP = X(MIN)X(MIN) = X(I)X(I) = TEMP

ELSEENDIF

50 CONTINUEC STAMPA DEL VETTORE RIORDINATO

PRINT -. 'vETTORE RIORDINATUD055 I=I,NPRINT *, X(I)

55 CONTINUESTOPEND

166

Page 88: Fortran

168

Esempio Il.20. Si vogliono calcolare le seguenti medie relative ai voti riportati

in 8 materie dai 60 alunni afferenti a tre classi di 20 alunni ciascuna:

1) la media dei voti riportati da ciascun alunno in ognuna delle tre classi;

2) la media dei voti per ciascuna materia in ognuna delle tre classi.

Tutti i dati possono essere contenuti in una variabile a tre dimensioni, di nome

V, in cui l'elemento vi,i,k indica il voto riportato nella j-esima materia dall'i-esimo

alunno della k-esirna classe; così gli indici di riga possono variare da l a 20,

quelli di colonna da 1 a 8, quelli di piano da l a 3.

I risultati dei calcoli sono contenuti in due matrici, MEDAL e MEDMAT: la

prima, di 20 righe e 3 colonne, contiene le medie relative al punto 1); la seconda,

di 8 righe e 3 colonne, contiene quelle relative al punto 2).

PROGRAM MEDIEC CALCOLO DELLE MEDIE PER ALUNNI E PER MATERIE

PARAMETER (NALUN = 20, NMAT = 8, NCLAS = 3)INTEGER V (NALUN, NMAT, NCLAS)REAL MEDAL (NALUN, NCLAS)REAL MEDMAT (NMAT,NCLAS)

C LETTURA DEI DATI,PER CLASSE,PER MATERIA, PER ALUNNOREAD -. V

C CALCOLO DELLE MEDIE RICHIESTE PER OGNI CLASSEDO 35, K = l, NCLAS 3

C CALCOLO DELLE MEDIEDEGLI ALUNNI DELLA K-ESIMA CLASSEDO lO, I = l, NALUNMEDAL (I, K) = O.DO S, J=I,NMATMEDAL (I, K) = MEDAL (I, K) + V(I, J, K)CONTINUEMEDAL (I, K) = MEDAL (I, K)/ NMAT

lO CONTINUEC CALCOLO DELLE MEDIERELATIVE AD OGNI MATERIAC NELLAK-ESIMA CLASSE

DO 20, J = l, NMATMEDMAT (J, K) = O.DO 15, I=I,NALUNMEDMAT (J, K) = MEDMAT (J, K) + V(I, J, K)

15 CONTINUEMEDMAT (J, K) = MEDMAT (J, K)/ NALUN

~O CONTINUE30 CONTINUE

C STAMPA DELLE MEDIE PER CLASSE,PER ALUNNOPRINT *, MEDAL

C STAMPA DELLE MEDIE PER CLASSE,PER MATERIAPRINT *. MEDMATSTOPEND

Si osservi che la frase READ *, V prevede la lettura dei 480 dati nel seguente

ordine: per ogni classe si devono fornire i voti riportati da tutti gli studenti nella

169

prima materia, poi i voti riportati da tutti nella seconda materia, e così via. Se i

dati non fossero disponibili in questo ordine si sarebbe costretti a riordinarli nel

modo imposto dal programma.

Esempio Il.21. Dati due vettori x, y di elementi xl' ... ,xn e Yl' ... 'Y n rispet­

tivamente, si vuole calcolare il prodotto scalare p, definito da

In [14] è dimostrato che l'accumulo degli errori di arrotondamento nel cal­

colo del prodotto scalare in precisione finita può essere notevole per alcune

scelte di x e Y e che può essere ridotto se si ha modo di eseguire le operazioni

con una precisione maggiore di quella in cui sono memorizzati i dati. Nel pro­

gramma seguente si calcola il prodotto scalare P in doppia precisione, mentre i

dati X e Y sono in precisione semplice. Si utilizza inoltre una variabile ausiliaria

D per poter eseguire tutte le operazioni in doppia precisione.

PARAMETER (N = lO)REAL X(N), Y(N)DOUBLE PRECISION D, PREAD*,X,YP = O.DODO 25 I = I, ND = X(I)p =P + D * Y(I)

25 CONTINUEPRINT -. 'VETTORE X v:', XPRINT *, 'VETTORE Y v .; YPRINT *, 'PRODOTTOSCALAREv:', PSTOPEND

Esempio Il.22. Data una matrice quadrata A, di ordine n, si vogliono calcolare

prodotti scalari p(j, k) fra la colonna j-esima e la colonna k-esima, definiti dan

p( j, k) = '\' a . a kL l,) l,

i= 1

per j = l, ... , n - l e k = j + 1, ... ,n. Si vuole inoltre interrompere il

calcolo appena si trova una coppia di valori (j ,k) per cui è Ip(j, k) I> E, dove

E> O è una costante assegnata. In questo caso l'esecuzione termina con la stampa

dei valori di j, k e p(j, k ). Se invece tutti i valori calcolati p(j, k ) sono in valore

assoluto minori o uguali di E. l'esecuzione termina con la stampa di un messaggio

che segnala tale situazione.

Page 89: Fortran

T171

scrivi: tutti i prodotti p sono "piccoli»

l ' ',', IDlMENSION VETT (O : 8)

DlMENSION APICE (8 : O)

REAL REC, REM (20,20)DlMENSION REC, REM (20, 20)

INTEGER MAT (5., 3,2) r (

DlMENSION ALFA (- 5, 2) /0 C

DlMENSION ALFA (- 5 : 2)

Il.5 Con riferimento alle variabili dimensionate dell'esercizio precedente, indi­

care quali fra i seguenti nomi di elementi sono sbagliati:BETA (2,3,4) GAMMA (2) DELTA (2) ALFA (2,3,4) ALFA (1,1)

EPSIL(3,4) ZETA (23,1) DELTA (O) ETA (2,3,4) ETA (2,33)

11.2 Scrivere opportune dichiarazioni per le variabili dimensionate qui di seguito

descritte:a) la matrice intera DAMA, di 12 righe e 12 colonne, con indici maggiori o

uguali di l;b) la matrice intera DAMB, di 12 righe e 12 colonne, con indici maggiori o

uguali di - 6;c) la matrice complessa COMP, con indici di riga variabili fra - 5 e 5 e indici

di colonna fra - 3 e 3;d) la variabile TRIANG, di tipo doppia precisione, di 3 righe, 5 colonne

e 4 piani, e indici non negativi;e) il vettore intero STATUS, con indici variabili fra - n e n, con n = 20.

11.3 Scrivere i dichiaratori di opportune variabili dimensionate atte alla memo­

rizzazione dei seguenti insiemi di dati:a) le temperature minima e massima rilevate in 20 stazioni metereologiche il

19 ottobre 1986;b) le temperature minima e massima rilevate in 20 stazioni metereologiche

nei giorni dal 20 al 26 ottobre 1986;c) i valori che la funzione f(x) = cosx assume nei punti xj = j ;- , per j = l,

.. , ,n;d) i valori che la funzione f(x, y) = x 2 + cos (xy) assume nei punti

(xi' Yk) = (j ; , k ;) con j, k = O, I, ... , n.

11.4 Indicare l'ampiezza delle seguenti variabili dimensionate:REAL ALFA (2:3,4), BETA (2,3,4), GAMMA (2,3:4), DELTA (234)

DOUBLE PRECISION EPSIL(2:3,4), ZETA(23,4), ETA (2,34).

EserciziIl.1 Individuare quali fra le seguenti frasi dichiarative sono sbagliate e spiegarne

il motivo:

per j = \, ... , n - I

Figura 11.5. Diagramma di flusso relativo all'esempio 11.22.

Il programma PROD che segue risolve il problema per n.ç l O, realizzando il

diagramma di fig. 11.5. Si osservi che in PROD si utilizzano due variahili ausi­

liarie, D e DP, in doppia precisione per poter effettuare i calcoli con una pre­

cisione maggiore di quella in cui sono memorizzati i dati e i risultati. Si osservi

inoltre che nel programma non si memorizzano tutti i valori p(j, k), bensi si usa

una variahile non dimensionata P per memorizzarli temporaneamente via via che

vengono calcolati.

PROGRAM PRODREAL A(IO, IO). P, EPSDOUBLE PRECISION D, DPREAD -. N. EPSDOl5 1=I,ND015 J=I,NREAD -, A (I, J)

15 CONTINUEDO I 50 J = I, N - I

D0140 K=J+I,NDP = O.DO00120 1=I,ND = A(I,J)DP = DP + D * A(I, K)

120 CONTINUEP= DPIF (ABS(P).LE.EPS) GOTO 140PRINT -. J, K, PSTOP

140 CONTINUE150 CONTINUE

PRINT -, 'P(1, K).LE.', EPS, 'PER OGNI (1, K)'STOPEND

170

Page 90: Fortran

j!

~ i

!l

'I, "

12Elaborazione delle informazionidi tipo carattere

DELTA (1)

ZETA (3 ** I, I)

DELTA (J + 1** 2)GAMMA (I, (I + 1)/3)

fra i seguenti nomi sono sbagliati e

BETA (2,3, 1/1) GAMMA (2, 1 - 7)

ZET A (I, 3 ** I)

ALFA (ABS(I- 5), 1/3)ETA (I, 1 -I)

Se 1= 2, 1 = IO, X = 3.14159, qualiperché?ALFA (1,1)

EPSIL (I, l/X)ETA (lNT(X), 34)ETA (J - I, I)

172

Il.6 Sono dati il vettore intero M e la matrice reale A dichiarati da

DIMENSION M (10), A( 10, lO)

Supponendo che il contenuto di M sia definito dalla sequenza di istruzioni

DOI3I=I,1O

M(I) = 2 * I - I13 CONTINUE

indicare la posizione corrispondente ai seguenti elementi:M(5), M(M(l)), M(M(2)), M(l + M(5»), M(lO), IA(l, lO), A(lO, l), A(M(5), M(4»), A(M(7)/3, lO), A(M(2) ** 2, I).

Nei capitoli precedenti si è più volte accennato al fatto che un calcolatore puòelaborare insieme alle informazioni di tipo logico o numerico anche informazionidi tipo carattere ovvero informazioni quali le lettere dell'alfabeto, le parole diun testo, i segni di interpunzione, etc. Negli ultimi anni, la manipolazione ed

elaborazione di informazioni di tipo carattere (word processing) ha notevol­

mente allargato le possibilità di applicazione degli elaboratori assumendo una

importanza sempre crescente che si manifesta anche nelle nuove possibilità di

gestione dei caratteri offerte dall'ultima versione standard del FORTRAN.

11.7 Scrivere un programma che permetta di definire gli elementi di una matrice

reale A di 5 righe e 7 colonne e di calcolare e stampare il massimo fra i valori

assoluti degli elementi di ciascuna riga. Provare la correttezza del programmaavendo come dato la matrice A i cui elementi a. . sono definiti da

l,l

i;;;:. ji + j

ai,j =i + j

i <i2i + 3j

11.8 Scrivere un programma che permetta di memorizzare in un vettore V le som­

me degli elementi di ciascuna colonna di una matrice reale B di ordine

n~ 15. Il programma deve inoltre riordinare in senso decrescente gli ele­

menti di V e stampare il vettore così ottenuto.

11.9 Scrivere un programma che permetta di leggere per colonne gli elementi di

una matrice A quadrata di ordine n ~ lO e calcolare e stampare le norme

Il A II~ e Il A 111' dove

12.1. Memorizzazione dei caratteri

Le informazioni di tipo carattere vengono memorizzate in unità di memoria

dette unità di memoria carattere ciascuna delle quali è in grado di contenere la

codifica binaria di un solo carattere. Le modalità con cui vengono codificati i

caratteri dipendono dal sistema usato che stabilisce anche la lunghezza di ogni

singola unità di memoria carattere. Y!!~~!na di codifica molto diffuso è quello

A~CIL~he, utilizzando 7 bits per la codifica di un carattere, permette di codifi­care 127 caratteri distinti. Un altro codice è quello EBCDIC che utilizza 8 bitsper la memorizzazione di un singolo carattere. Con il co~Ùce-EBCDIC è possibile

definire ed utilizzare 256 caratteri diversi. Sia il codice ASCII che quello EBCDICsono riportati in appendice A4.

Le unità di memoria carattere sono quindi completamente diverse e netta­mente distinte da quelle numeriche che, ricordiamo, sono destinate a contenereinformazioni di tipo numerico o logico. Tale distinzione è chiaramente sottolinea­ta dallo standard F77 che definisce dato di tipo carattere una qualunque succes­

sione (stringa) di caratteri codificabili su un elaboratore ed associa ad ogni dato ditipo carattere la sua lunghezza definita come il numero di caratteri che lo costi­

tuiscono. Un dato di tipo carattere è quindi memorizzato in tante unità di memo­ria carattere contigue quante sono quelle specificate dalla sua lunghezza.

Page 91: Fortran

•I

174175

Esempio 12.2. La frase:

CHARACTER * 12 XI, X2, X3 * IO.

CHARACTER * 7 A, B, H * 3, C, D

CHARACfER * I A, B, C

CHARACTER A * I, B * 5, C * ICHARACTER XY * 4

CHARACTER X * 33. Y * 33

che equivale a

che equivale a

che equivale a

che equivale a

CHARACTER A, B, C

CHARACTER A, B * S, C

CHARACTER * 4 XY

CHARACTER * 33 X. Y

lunghezza di nomi simbolici di costanti (ulteriori utilizzazioni di questo specifi­catore sono indicate nel cap. 15).

Lo specificatore di lunghezza ~ che segue la parola chiave CHARACTER fissa

la lunghezza per tutte le entità carattere individuate dai nomi simbolici nl' ... , nrmentre ogni specificatore di lunghezza che segue un nome sim bolico si riferisce

soltanto alla entità individuata da quel nome. Gli specificatori che fissano lun­

ghezze uguali ad uno possono essere omessi insieme all'asterisco che li precede.

In una frase CHARACTER è sempre possibile specificare la lunghezza di una

entità di tipo carattere facendo seguire il corrispondente nome simbolico da

un asterisco e da uno specificatore di lunghezza. In_particolare è possibile indicare

una lunghezza diversa da quella fissata dallo specificatore Q che segue la parola

chiave; in questo caso lo specificatore di lunghezza Q fissa la lunghezza per tutte

le entità i cui nomi sim bolici non sono seguiti da un loro specificatore di lunghez­za che, in generale, è diverso da Q.

CHARACfER A * 7, B * 2, C * (3 + 8)

specifica che A, B e C sono entità carattere la cui lunghezza è rispettivamenteuguale a 7, 2, II.

Altri esempi di dichiarazione esplicita di tipo carattere sono i seguenti:

Esempio 12.1. La frase dichiarativa di tipo:

CHARACTER * 7 A, B, C

specifica che A, B e C sono entità carattere ciascuna delle quali contiene esatta­mente 7 caratteri. La frase.

specifica che A, B, C, D sono nomi simbolici di entità carattere la cui lunghezza

è uguale a 7 mentre H indica il nome di una stringa di caratteri la cui lunghezza

è uguale a 3; analogamente, per dichiarare che le varia bili X I, X2 e X3 sono di ti.

po carattere ed hanno lunghezza rispettivamente uguale a 12, 12, IO si può usarela frase:

dove:

• CHARACfER è la parola chiave che identifica la frase;

• n l , n2, ... , n r sono nomi simbolici; . .. .• Q Q ,Q2" .. , Q sono specificatori di lunghezza ciascuno del quali può essere., I r

- una costante intera positiva non preceduta dal segno +;- una espressione costante intera che deve avere valore positivo e deve essere rac-

chiusa tra parentesi; ..- un asterisco racchiuso tra parentesi (*) che può essere usato per specificare la

Variabili carattere

Le variabili di tipo carattere (variabili carattere) vengono indicate mediante un

nome simbolico; il loro tipo deve essere specificato mediante una opportuna frase

dichiarativa nella quale sono indicati sia il nome della variabile che la sua lun­

ghezza.

Dichiarazione esplicita del tipo carattere

Per specificare il tipo e la lunghezza di una entità di tipo carattere è possibile

usare una delle seguenti forme della frase dichiarativa CHARACfER:

CHARACTER .. Q "l' "2' ..., nr

CHARACTER "r " QI' "2 .. Q2' ... , "r .. Qr

12.2. Le costanti e le variabili di tipo carattere

Costanti carattere

Una costante di tipo carattere (costante carattere) è scritta in FORTRAN

come una successione di caratteri racchiusa tra apici. Gli apici che racchiudono la

costante non fanno parte di essa e quindi tra i due apici che delimitano una co­

stante carattere deve esserci almeno un carattere che può essere anche il carat­

tere di spaziatura (blank). Una costante carattere può essere costituita sia da ca­

ratteri facenti parte dell'alfabeto FORTRAN che da caratteri diversi qual:, ad. <:;;;. [ l?' . % purché codificati sul sistema di calcolo usato. L apo-esempiO, ,"'-, ".,.,,,

strofo è rappresentato da una coppia di apici consecutivi. . .

Indicato con v il carattere di spaziatura sono esempi di costanti carattere I se­

guenti:

'BUONGIORNO' '1987' 'COMEvSTAI?' 'c"ERA' 'vUNv' 'v'.

Si osservi che la costante '1987' rappresenta la successione di quattro caratteri:

I, 9, 8, 7 e non il numero 1987. . .

La l',lghezza di una costante carattere è il numero dei caratte~ ~resentl tra gliapici, compresi eventuali caratteri di spaziatura; il doppio apice u~iliz_z~~._~er~ap­

'--\-- presentare l'apostrofo conta come un_unico carattere. Così le sei costanti pnma

~~riit~hannorispettivamente lunghezza 10,4, IO, 5, 4, l.

Il

,l

Page 92: Fortran

176

Esempio 12.3. Consideriamo la seguente successione di frasi dichiarative:

PARAMETER (LUN = 6, L = 8)CHARACTER • (LUN) VOCE, TIPO, ART. (L)PARAMETER (ART = 'ARTICOLO').

La prima frase PARAMETER stabilisce il valore degli specificatori di lunghezza

usati nella dichiarativa CHARACfER; la seconda frase PARAMETER assegna in­

vece alla costante carattere'ARTICOLO' il nome simbolico ART. Questa succes­

sione di istruzioni serve allora a specificare che VOCE e TIPO sono due variabili

carattere di lunghezza uguale a 6 mentre ART è il nome simbolico della costantecarattere'ARTICOLO' di lunghezza 8.

Come si vede anche da questo esempio quando la frase CHARACfER è usata

per dichiarare il tipo di un nome simbolico di costante, il valore di questa costante

deve essere specificato in una frase PARAMETER che segue la dichiarativa

CHARACfER. In questo caso la lunghezza della costante carattere può essere in-

. dicata mediante lo specificatore (.) che chiameremo specificatore di lunghezza in­

defi.'!!ta; la sua utilizzazione ha l'effetto di specificare, pedeeritiiàCa~attere'indi­

viduate da nomi simbolici di costante, una lunghezza uguale a quella delle corri­spondenti costanti che compaiono nella frase PARAMETER. In ogni caso, una

volta fissata, la lunghezza di un nome simbolico di costante carattere non deveessere più modificata.

Esempio 12.4. Le frasi:

CHARACTER • ( • ) SP, CARPARAMETER (SP = 'SPECIFICAZIONE', CAR = 'CARATTERE')

servono a specificare che SP e CAR sono nomi simbolici di due costanti carattere la

cui lunghezza è uguale, rispettivamente, a quella delle costanti 'SPECIFICAZIONE'

e 'CARATIERE' indicate nella dichiarativa PARAMETER. Pertanto SP halunghezza 14 e CAR ha lunghezza 9.

Esempio 12.5. La successione di istruzioni:

PARAMETER (LUN = 6)CHARACTER • (LUN) VOCE, TIPO, ART. (.)PARAMETER (ART = 'ARTICOLO')

ha lo stesso effetto di quella indicata nell'esempio 12.3. In questo caso la lunghez­

za della costante il cui nome simboli co è ART è determinata da quella della co­

stante 'ARTICOLO' ed è quindi uguale a 8. Se la seconda frase PARAMETERvenisse sostituita da

l

177

PARAMETER (ART = 'ARTICOLO V'DAV' REGALO')

il nome simbolico ART indicherebbe una costante carattere di lunghezza uguale

a 18.

Dichiarazione implicita del tipo carattere

Analogamente a quanto detto per le entità di tipo numerico o logico è possi­

bile indicare in un programma FORTRAN che una o più lettere dell'alfabeto,

se usate come iniziale di un nome simbolico, ne determinano il tipo carattere.

La frase che permette la dichiarazione implicita del tipo carattere ha la forma:

IMPLICIT CHARACfER * {I (al' a2, ••• , am)

dove:• IMPLICIT CHARACfER è la parola chiave che identifica la frase;

• Q è uno specificatore di lunghezza diverso da (*);

• al' a2, ... , a

msono singole lettere oppure gruppi di lettere ordinate alfabetica­

mente di cui viene indicata la prima e l'ultima lettera separate da un segno meno.

Nella dichiarazione im!'.li~~~u~~.tip().!\on è quindi l::0!1~~!!!i!~l'_~~odello speci­ficatore di lunghezza indefinita;)noltre, i nomi il cui tipo è implicitamente speci­

ficato dalla frase IMPLICIT CHARACfER indicano stringhe di caratteri che

hanno tutte la stessa lunghezza: quella fissata dallo specificatore Q. Così, ad esem­

pio, la frase:

IMPLICIT CHARACfER * 16 (A - C)

specifica che i nomi simbolici che iniziano con le lettere A, B, C indicano entità

di tipo carattere di lunghezza 16. Una dichiarazione esplicita di tipo può modifi­

care il tipo o la lunghezza delle entità i cui nomi hanno una lettera iniziale pre­

vista in una istruzione IMPLICIT CHARACTER.

Esempio 12.6. La successione di istruzioni:

IMPLICIT CHARACTER. 16 (A - C)REA L ANNA, CARLOCHARACTER • 8 BABBO

ha l'effetto seguente: tutte le variabili i cui nomi hanno come lettera iniziale

A, B oppure C sono considerati di tipo carattere e la loro lunghezza è uguale a 16

unità di memoria carattere. Fanno eccezione ANNA e CARLO che indicano

variabili reali e BABBO che indica una variabile carattere di lunghezza 8. Si noti

che la dichiarazione implicita di tipo precede quella esplicita secondo le regole

già viste nel § 5.3.

Page 93: Fortran

178 179

Esempio 12. 7. caratteri. Una sottostringa è identificata da un nome la cui forma è la seguente:

Esempio 12.11. Sia AI una variabile carattere di lunghezza 5 il cui contenuto è

la stringa GAMMA. Indichiamo, accanto ad ogni nome. i caratteri che costitui­

scono alcune sottostringe estratte da A I e le relative lunghezze.

Esempio 12.10. Supponendo che ALFA sia una variabile carattere di lunghezza 8e BETA sia un vettore carattere di tre componenti di lunghezza 5, il nome simbo­

lico ALFA(2 : 5) indica la sottostringa formata dal secondo, terzo, quarto e quin­

to carattere della stringa di nome ALFA mentre BETA(2)( 1: 3) identifica la

sottostringa costituita dai primi tre caratteri di BETA (2).

dove:

• v è il nome della variabile carattere o dell'elemento di variabile carattere

dimensionata da cui si estrae la sottostringa;

• et, e2 sono due espressioni intere dette espressioni di sottostringa. II valore di

et specuica la posizione nella variabile v del carattere più a snustra della sotto­

stringa mentre il valore di e2

specifica quelIa del carattere più a destra. I valori di

et ed e2 devono essere tali che 1 ~ et ~ e2 ~ Q dove Q è la lunghezza di v.

3

I

Lunghezza

5

Contenuto

GAMMA

AM

MA

GAM

A

Sottostringa

Al (:)

A I (2 : 3)

Al (4 :)

A l( : 3)

Al(2:2)

In un nome sim bolico di sottostringa possono essere omesse una o entrambe

le espressioni di sottostringa: l'omissione di et equivale ad e, = l, quella di e2 equi­

vale ad e2 = Q; se entram be le espressioni sono omesse il nome della sottostringa

ha la forma v(:) e la sottostringa coincide con l'intera stringa v.

La lunghezza di una sottostringa è data da e2 - e, + l. Pertanto, se il valore di

e, è uguale a quello di e2 la sottostringa è costituita da un unico carattere, quello

che nella stringa v occupa la posizione indicata da et e da e2

.

Variabili carattere dimensionate

Nel capitolo precedente è stata sottolineata l'opportunità di utilizzare variabili

dimensionate che, ricordiamo, possono essere anche di tipo carattere. La frase

dichiarativa CHARACTER può essere utilizzata per specificare i nomi delle even­

tuali variabili dimensionate, il numero e la lunghezza dei loro elementi. ~?-g~i

caso, tutti gli elementi di una variabile carattere dimensionata devono avere)~

stessa lunghezza ed è pertanto proibito usare variabili carattere dimensionate che

siano costituite da elementi di lunghezza diversa l'uno dalI' altro.

CHARACTER * lO VOCE (5)

Esempio 12.8. La frase:

Esempio 12.9. La successione di istruzioni:

IMPLICIT CHARACTER. 25 (A)DIMENSION ART (IO)

serve a specificare che le variabili i cui nomi sim bolici iniziano con la lettera A

sono di tipo carattere ed hanno lunghezza 25; inoltre ART è un vettore carattere

di lO elementi ciascuno dei quali è costituito da 25 caratteri.

specifica che VOCE è una variabile dimensionata costituita da cinque elementi

di tipo carattere ciascuno dei quali ha lunghezza uguale alO.

PARAMETER (LUN =3)IMPLICIT CHARACTER. (LUN + 2) (A - C F, M)CHARACTER F I • (LUN + I), MAM • 15PARAMETER (FI = 'CANE', F2 = 'GATTO')

La prima frase PARAMETER fissa il nome LUN per la costante 3; la seconda

frase stabilisce che tutti i nomi che iniziano con le lettere A, B, C. F, M si riferi­

scono a quantità carattere di lunghezza uguale a 5; la terza frase specifica che F 1

e MAM, pur essendo sempre di tipo carattere, hanno però una lunghezza diversa

rispetto a quelIa specificata implicitamente: F 1 ha lunghezza 4 e MAM ha lun­

ghezza 15; la quarta frase infine assegna alla costante 'CANE' il nome simbolico

Fl ed alIa costante 'GATTO' il nome simbolico F2. Si osservi che 'CANE' e

'GATTO' sono costituite rispettivamente da 4 e da 5 caratteri.

li

I

II

II\i\

I

!i IIl

!\

liI

12.3. Sottostringhe ed espressioni carattere

Sottostringhe

Con il termine sottostringa si indica in F77 una entità di tipo carattere costi­

tuita da un qualunque sottoinsieme di caratteri contigui estratti da una stringa di

Espressioni carattere

Una espressione carattere è costituita, nella sua forma più semplice, da una

delIe seguenti entità carattere: costante, variabile, elemento di variabile dimen­

sionata, sottostringa. Espressioni carattere più complesse possono essere formare

usando l'operatore concatenazione che viene indicato con il simbolo Il e che

Page 94: Fortran

180181

opera tra due operandi di tipo carattere. Se xl ed x2

indicano due entità carat­

tere il risultato dell'operazione

è una stringa carattere il cui valore è quello di xl seguito dal valore di x2.

Esempio 12.12. Il valore dell' espressione carattere:

'LIN' Il 'GUAGGIO'

è la stringa LINGUAGGIO ottenuta congiungendo in un'unica stringa i valori

delle costanti 'LIN' e 'GUAGGIO'. Analogamente l'espressione:

'LINGUAGGIO' Il 'v' Il 'FORTRAN' Il '77'

Esempio 12.14. La successione' di istruzioni:

CHARACTER * 4 VETT(5), A(2, 2)VETT(l) = 'CANE'VETT(2) = 'LUPO'VETT(3) = 'GUFO'VETT(4) = 'IENA'VETT(5) = 'TOPO'DO IO I = 1,2DO IO J = 1,2A(I, J) = VETT (2 * J - 2 + I)

lO CONTINUE

specifica la lunghezza ed il contenuto sia delle cinque componenti del vettore

carattere VETT che dei quattro elementi della matrice carattere A.

ha il seguente valore:

LINGUAGGIOvFORTRAN 77.

Esempio 12.15. Sia A I una variabile carattere il cui valore è la stringa NUOVO.

L'esecuzione della frase:

A\(4 : 4) = 'T'

Esempio 12.16. Consideriamo la successione di istruzioni:

Dopo l'esecuzione di queste istruzioni V(I), V(l) e V(3) contengono rispettiva­

mente i valori:

sostituisce. il quarte carattere di A I con la lettera T. II contenuto di A l diventa

quindi la stringa NUOTO.

CHARACTER * 6 V(3), Al * LU, AL * I~

Al = 'ILvGATTOvEvLAvVOLPEv'A2 = 'ILvGRILLOvPARLANTE'V(l) = Al(4 : 9)V(2) = AI(l5 :)V(3) = A2(4 : 9)

GRILLOVOLPE vGATTO v

v = espressione carattere

12.4. Assegnazione fra stringhe di caratteri

Come è stato sottolineato nel cap. 7, la frase di assegnazione può essere definita

anche tra variabili ed espressioni di tipo carattere. La forma generale della frase

è in questo caso:

dove:

• v è il nome di una variabile carattere, di un elemento di variabile carattere di­

mensionata, di una sottostringa.

L'esecuzione di questa frase implica la valutazione dell'espressione carattere

e la successiva definizione di v il cui valore viene posto uguale a quello dell'espres­

sione se la lunghezza di v è uguale a quella del valore dell'espressione carattere.

Esempio 12.13. La successione di istruzioni:

CHARACTER * 7 AN, SAN = 'CAVALLO'

S=AN

permette di memorizzare l'informazione carattere 'CA VALLO' nelle variabiliAN ed S.

In una frase di assegn...a. zione la variabile v può avere lunghezza diversa dal

<.~./valor~Q.cll'espressionecarattere;in questo caso la stringa che costituisce il valore "

. dell'espressione viene opportunamente «allungata» o «troncata» prima di effet­

tuare l'assegnazione. A questo proposito il FORTRAN specifica che se la lunghez­

~--di. v~ ~~g~iore di quella del valore dell'espressione, quest'ultimo viene allun­

gato con l'aggiunta, alla sua destra, di tanti caratteri blank quanti ne servono

per uguagliare la lunghezza di v; se la lunghezza di v è invece inferiore a quella

del valore dell'espressione carattere, quest'ultimo viene accorciato togliendo, alla

________________-----J..-------- _

Page 95: Fortran

182

sua destra, tanti caratteri quanti ne occorrono per uguagliare la lunghezza di v.

r183

razioni di concatenazione e le frasi di assegnazione tra stringhe di lunghezza

diversa.Esempio 12.17. Sia A una variabile carattere di lunghezza 6. Indichiamo, accanto

ad alcune frasi di assegnazione, il contenuto di A:

Esempio 12.18. Sia DATO una variabile carattere di lunghezza uguale a 5. Esami­

niamo l'effetto dell'esecuzione sequenziale di alcune frasi di assegnazione.

Frase di assegnazione

A= 'UN'

A = 'VELOCEMENTE'A = 'PINO'II'LORO'

Frase di assegnazione

DATO = 'FERRO'DATO (I :4) = 'CORT'DATO (4:4) = 'V'DATO (2:2) = 'ERBA'DATO (4 :) = 'A'

Contenuto di A

UNVvvvVELOCEPINOLO

Contenuto di DATU

FERROCORTOCORVOCERVOCERAV

Esempio 12.19.

CHARACTER VAR * 8, TAR * IOVAR = 'AUTO'

TAR = VAR l l 'MOBILE'

La prima frase di assegnazione colloca la stringa AUTO nelle prime quattro

posizioni di VAR il cui contenuto è completato da caratteri di spaziatura fino a

raggiungere la lunghezza di 8 caratteri fissata per VAR. Per eseguire la seconda

frase di assegnazione si valuta l'espressione carattere VAR /1 'MOBILE' il cui

valore, AUTOvvvvMOBILE, è costituito da 14 caratteri ed è quindi troncato

in AUTOvvvvMO prima di essere assegnato come contenuto della variahile

TAR. Un risultato diverso sarebbe stato ottenuto concatenando una sottostringa

di VAR con la costante carattere 'MOBILE' ovvero usando la frase di assegnazione

TAR = VAR (: 4) Il 'MOBILE'.

Le ultime due frasi dell'esempio precedente mettono in evidenza che, al mo­

mento della assegnazione, si applica sempre la regola di «aggiustare opportuna­

mente» la lunghezza del valore dell'espressione in modo che essa coincida conquella di v anche quando v è una sottostringa.

Si osservi che in una frase di assegnazione tra stringhe di caratteri è proibitaqualunque sovrapposizione tra le unità di memoria carattere che costituiscono

v e quelle utilizzate dall'espressione. Pertanto sono sbagliate le frasi seguenti:

DATO (I :4)='LE' Il DATO (2 :8)DATO = DATO (l : 3) Il VARDATO = DATO (: 2) Il DATO (9:)DATO (3: 5) = DATO (4: 4) Il DATO (l : 3)

in quanto in ognuna di esse la valutazione dell'espressione carattere coinvolge

l'elaborazione di sottostringhe che si sovrappongono con quelle indicate a sinistra

del simholo di assegnazione. Sono invece esempi di frasi corrette i seguenti:

DATO (I :4) = 'LE' Il DATO (5 :8)DATO (4:) = DATO (: 3)

DATO (3 :5)=DATO(:2)IIDATO(6 :6)DATO (2 : 2) = DATO (3: 3)

L'esempio seguente serve ad evidenziare quali effetti possano produrre le ope-

L'espressione carattere che compare in questa frase ha infatti come valore la

stringa AUTOMOBILE.

12.5. Lettura e scrittura dei dati di tipo carattere

Le frasi di ingresso/uscita guidate dalla lista introdotte nel cap. 8 possono essere

usate per leggere e scrivere quantità di tipo carattere; altre possibilità per effet­

tuare queste operazioni verranno presentate nel prossimo capitolo. Si ricordi che

le costanti carattere possono far parte di una lista di una frase PRINT* ma non

di una READ* mentre sia la lista di ingresso che quella di uscita possono conte­

nere nomi simbolici di entità carattere.

Esempio 12.20.

CHARACTER * 8 AN I, AN2READ *, N, M, ANIAN2 = 'V PECORE v'PRINT -. 'ClvSONOv', N, AN2, 'vEV', M, ANISTOPEND

Il significato e l'effetto di queste istruzioni è di immediata comprensione e

non necessita di ulteriori spiegazioni, Si deve però osservare che i dati devono

Page 96: Fortran

. \

184

essere fomiti in modo opportuno: i primi due dati devono essere costanti intere

e saranno quindi costituiti da una stringa di cifre decimali mentre il dato di

tipo carattere sarà costituito da una costante di lunghezza 8 (per esempio

'v MUCCHEv').

Per quanto riguarda l'operazione di lettura guidata dalla lista si deve tenere

presente che essa equivale ad una frase di assegnazione nel senso che permette

di definire il contenuto di una variabile o di una sottostringa di caratterL!'.~r­

tanto, se la lunghezza del dato fornito in ingresso non è uguale a quella stabilita

per la corrispondente variabile o sottostringa, essa viene automaticamenteaggiu­

stata togliendo caratteri a destra del dato o aggiungendo caratteri di splgia!,:!ra

sempre a destra del dato secondo le modalità viste per le frasi di assegnaz~e.

Esempio 12.21. Sia VAR una variabile carattere di lunghezza 5 il cui valore viene

definito dalla frase di ingresso

REA D *, VAR

Se viene fornito il dato' AUTOMOBILE', il valore di VAR è costituito dai primi

cinque caratteri di questa stringa ovvero VAR vale AUTOM; se in ingresso viene

fornita la stringa 'AUTO' il valore di VAR è AUTOv.

Nelle operazioni di scrittura guidate dalla lista il numero di caratteri che devono

essere riprodotti in uscita è determinato dalla lunghezza della espressione carat­

tere che compare nella lista di uscita: il valore dell'espressione viene interamente

riprodotto sul mezzo di uscita standard.

Esempio 12.22.

CHARACTER TESTO * 3TESTO = 'F77'DO lO 1= 1,3PRINT ... , TESTO (I : I)

lO CONTINUESTOPEND

L'esecuzione di questo programma produce la scrittura dei singoli caratteri

della stringa F77 su righe successive, ovvero:

F7

7

185

12.6. Confronto tra espressioni carattere

E' possibile utilizzare gli operatori di relazione .GT., .LT., .GE., .LE., .EQ.,

.NE. definiti nel §6.2 per eseguire confronti tra due stringhe di caratteri ovvero è

possibile definire ed utilizzare una espressione relazionale carattere il cui valore

è «vero» oppure «falso». Così, ad esempio, supponendo che VOCE e TESTO

siano i nomi simbolici di due variabili carattere entrambe di lunghezza lO, sono

corrette le seguenti istruzioni di controllo che coinvolgono espressioni relaziona­li carattere:

IF (TESTO.GT.VOCE) TESTO (l: 3) = 'ALB'IF (TESTO (3: 5).LT.VOCE (3: 5» GOTO lOIF (TESTO.EQ.' AUTOMOBILE') VOCE = 'DAvCORSA'IF (VOCE.NE.TESTO (l: 5) Il 'CARTA') VOCE = 'PENNA'

Per capire le modalità secondo le quali viene valutata un'espressione reiazionalecarattere, occorre tener presente che:

• l'ordinamento alfabetico delle lettere equivale ad un ordinamento in sensocrescente ovvero:

A<B<C< ... < X<Y<Z

• le cifre decimali sono ordinate in senso crescente:

0<1<2< ... <8<9

• l'insieme costituito dalle lettere dell'alfabeto e dalle cifre decimali deve essereordinato in uno dei modi seguenti:

0< I <2< ... <8<9<A<B< ... <Y<Z

A<B< ... <Y<Z<O< l < ... <8<9

la scelta tra questi due ordinamenti è lasciata al singolo sistema di calcolo;

• il carattere blank precede sia la lettera A che la cifra zero cioè blank < A eblank < O.

Altri caratteri diversi dalle lettere dell'alfabeto, dalle cifre decimali e dalla

spaziatura costituiscono un insieme il cui ordinamento non viene fissato dal

FORTRAN ma dal sistema di calcolo su cui si lavora. Nel prossimo paragrafo

vedremo come è possibile utilizzare mediante opportune funzioni intrinseche,l'ordinamento dei caratteri del sistema di codifica ASCII e rendere pertanto indi­

pendente dall'elaboratore usato il risultato del confronto tra espressioni carattere.

Il confronto tra due operandi di tipo carattere avviene nel modo seguente:

• se i due operandi hanno lunghezza diversa, quello più corto viene allungatoaggiungendo caratteri blank alla sua destra;

: ~~ i

Page 97: Fortran

186187

• i due operandi vengono confrontati a partire dal loro carattere iniziale: è

«maggiore» l'operando che ha il carattere iniziale maggiore. Se i caratteri ini­

ziali sono uguali il confronto tra i due operandi procede carattere per carattere

fino a che non si trovano due caratteri diversi: la relazione tra questi due carat-

i teri determina quella tra i due operandi;

\. due operandi sono uguali se sono costituiti da stringhe di caratteri uguali.

Esempio J2.23. Le relazioni tra stringhe di caratteri:

'GIANNI'.GT.'AGUZZI''MARIA'.GT.'MACCONI''GRAZIA'.GT.'GASPARO'

sono tutte vere. La veridicità della prima espressione è determinata dal1a rela­

zione che lega le lettere iniziali dei due operandi, quella del1a seconda dalla

relazione che lega il terzo carattere dei due operandi e quella della terza dal1a

relazione che lega il secondo carattere dei due operandi.

E' ancora «vero» il risultato del1'espressione:

Esempio J2.25. Si vuoI scrivere un programma che, letta una stringa di 7 carat­

teri alfabetici, permetta di stabilire se la lettera iniziale e quella finale della stringaprecedono M e quante volte compare nella stringa la lettera B.

CHARACTER * 7 VARREAD *, VARIF (VAR(I: 1).LT.'M'.AND.VAR(7: 7).LT.'M') THEN

PRINT -. 'LAVLETTERAvINIZIALEVPRECEDEvM'PRINT *, 'LAvLEITERA vFINALEvPRECEDEvM:

ELSE

PRINT -. 'LAVLETTERAvINIZIALEVNONvPRECEDEVMvOPPURE'PRINT *, 'LAvLETTERAvFINALEvNONvPRECEDEvM'

ENDIFNB =0DO IO 1=1,7IF (VAR(I: I).EQ.'B') NB = NB + I

IO CONTINUE

PRINT *, 'LAvLETTERAvBVCOMPARE', NB, 'vVOLTE'STOPEND

'GENNAIO vI986'.LT.'GENNAlO v1987'

LLT CIvMAGGlOv 1986', 'l vMAGGIO vI987')

12.7. Funzioni intrinseche per la manipolazione dei caratteri

Le funzioni LGE, LGT, LLE, LLT

Nel paragrafo precedente è stato osservato che è possibile confrontare tra loro

due stringhe di caratteri indipendentemente dal sistema di codifica usato dal sin­

golo elaboratore. II FORTRAN prevede infatti quattro funzioni intrinseche LGE,

LGT, LLE, LLT ciascuna delle quali permette di confrontare due espressioni

carattere secondo l'ordinamento definito nel sistema di codifica ASCII. Queste

quattro funzioni operano su due argomenti ciascuno dei quali è costituito da una

espressione carattere di lunghezza arbitraria; il risultato di ciascuna funzione è

un valore logico che rappresenta il risultato del confronto tra i due argomentieseguito secondo il codice ASCII. Più precisamente:

Esempio J2.26. II valore dell'espressione:

Cl ~ c2

cl> c2Cl .ç c2

Cl < c2 ·

dà risultato vero se

dà risultato vero se

dà risultato vero se

dà risultato vero se

LGE (Cl' c2)

LGT (cl' c2)

LLE (Cl' c2)

LLT (Cl' c2)

'I vMAGGlOvI986'.LT.'1 vMAGGIO v1987'

CHARACTER * IO DATOREAD -. DATOIF(DATO(I :I).EQ.' A'.AND.DATO (IO:IO).EQ.'1') THEN

PRINT *, 'LAvSTRINGAvINIZIAvCONvA vE vTERMINAvCONvl'ELSE

PRINT -. 'CARATTEREvINIZIALEv', DATO(I:I)PRINT *, 'CARATTEREvFINALEv', DATO(10:10)

END IFSTOPEND

mentre dipende dal sistema usato il valore dell'espressione:

Esempio J2.24. Si vuoI scrivere un programma che, letta una stringa di IO carat­

teri, permetta di stabilire se essa inizia con la lettera A e termina con la lettera I.Nel caso in cui questo non sia verificato, il programma deve stampare il carattere

iniziale e quello finale del1a stringa data in ingresso.

Vediamo ora alcuni esempi di programmi che prevedono confronti tra stringhe

di caratteri.

in quanto il FORTRAN non specifica quale sia l'ordinamento tra lettereecifre.

Page 98: Fortran

188

è «falso» in quanto nel codice ASCII l'insieme delle cifre decimali precede quello

delle lettere dell'alfabeto e quindi, in particolare, I> l.

La funzione INDEX

La funzione intrinseca INDEX permette di localizzare in una stringa di carat­

teri il punto in cui compare un'altra stringa di caratteri. La funzione lNDEX ha

due argomenti di tipo carattere: il primo, sI' identifica la stringa che deve essere

analizzata, il secondo, s2 ' indica la stringa che deve essere localizzata dentro sI'

II risultato della funzione INDEX (SI' s2) è un valore intero che indica la posizio­

ne del carattere iniziale di s2 nella stringa SI' Se s2 compare più di una volta in

SI il risultato di INDEX (SI' s2) è la posizione del carattere iniziale della prima

occorrenza di s2 in SI . Il risultato di INDEX (sI' s2) è zero se s2 non compare inSI oppure se la lunghezza di s2 è maggiore di quella di SI'

Pertanto il risultato di:

INDEX ('IL'I7NOME'I7DELLA 'I7ROSA', 'NOME')

è 4 perché la stringa NOME si trova nella stringa IL '17 NOME '17 DELLA '17 ROSA a

partire dal quarto carattere. Analogamente, 12 è il risultato di:

INDEX ('IL '17 NOME '17 DELLA '17 ROSA', 'LA')

189"

PARAMETER (LLIN = 70, LUN = 4)CHARACTER LINEA * (LLIN), ART * (LUN)INTEGER POSNUM=OREAD -. LINEAART = ''I7UN'I7'LOC= lDO lO I = l, LLIN/LUNPOS = INDEX(LINEA(LOC :), ART)IF (POS.EQ.O) GO TO 20LOC = POS + LUN+ LOC- 1NUM = NUM + lPRINT *, ART, 'COMPARE'I7NELLA'I7POSIZIONE'I7', (POS + LOC- l)

lO CONTINUE20 PRINT *, 'NUMER0'l7D1'170CCORRENZE'I7D1'17', ART, NUM

STOPEND

11 multato dell'espressione lNDEX (LINEA (LOC:), ART) indica la DosizioJ1e

di ART nella sottostringa LINEA (LOC:). Così quando LOC vale I, POS indica

J;pc;sizione in LINEA-della prima occorrenza di ART. Successivamente il conte­

nuto di LOC viene modificato in modo da analizzare la stringa LINEA a partire

dalla posizione LOC che segue immediatamente quella dell'ultimo carattere di

ART. Supponendo che la stringa memorizzata in LINEA sia:

UNA DONNA VIDE UN GATIO CHE SALTAV A SUL PRATO DA UN RAMO DI UN ALBERO

la successione di valori delle variabili LOC e POS è la seguente:

,I

La funzione ICHAR ha come argomento un'espressione carattere di lunghezza

uno (ovvero un singolo carattere) e dà come risultato un valore intero che rappre­

senta la posizione del carattere nel sistema di codifica usato dall'elaboratore. 11FORTRAN specifica che se un sistema prevede la codifica di n caratteri il risultato

di ICHAR dovrà essere un intero compreso tra zero ed (n - I). Evidentemente,

l'argomento di lCHAR deve essere un carattere rappresentabile sul sistema usato.

La funzione CHAR ha come argomento una espressione intera, i, il cui valore

deve essere compreso tra zero ed (n - l) essendo n il numero di caratteri codifi­

cati sull'elaboratore u

Le funzioni ICHAR, CHAR e LEN

mentre zero è il risultato di:

INDEX ('IL '17 NOME 'I7DELLA '17 ROSA', 'ROSSA')

INDEX ('NOME', 'IL '17 NOME 'I7DELLA 'I7ROSA')

La funzione INDEX può essere utilizza la ad esempio per risolvere il problema

di determinare il numero totale di occorrenze di una data stringa in una più lunga

e, in generale, per determinare il numero di volte che una certa espressione lessi­cale è usata in un testo.

Esempio 12.27. Si vuoi scrivere un programma che permetta di calcolare il nume­

ro di volte che l'articolo indeterminativo UN compare sulla riga di una pagina di

un libro. Si vogliono inoltre individuare le posizioni delle singole occorrenze del­

l'articolo UN nella riga che supporremo composta da 70 caratteri.

Indicata con LINEA la variabile carattere che contiene la riga da esaminare e

con NUM il numero totale di occorrenze della stringa' '17 UN '17' in LINEA, un

programma che permetta di risolvere il problema è il seguente:

Valore di

LOC

l

19

53

64

Caratteri analizzatiin LINEA

dal primo al 70-mo

dal 19-mo al 70-mo

dal 53-mo al 70-mo

dal 63-mo al 70-mo

Valore diPOS

15

49

60

O

Page 99: Fortran

T190

191

Il risultato di CHAR (i) è il carattere corrispondente alla i-ma posizione nel si­stema di codifica usato. Evidentemente se I è un intero tale che O ,ç I ,ç n - l edX è un carattere codificato si ha che:

Il FORTRAN prevede per la elaborazione delle informazioni carattere un'altrafunzione intrinseca, LEN(c), il cui risultato è la lunghezza dell'espressione carat­

tere che costituisce il suo argomento. L'utilizzazione di questa funzione verràesemplificata nel cap. 15.

Esempio 12.28. Si vuoi scrivere un programma che permetta di sostituire ad

ogni lettera di una stringa di caratteri quella che la segue nell'alfabeto e lasci inal­terati i caratteri non alfabetici. La lettera Z deve essere sostituita dalla A.

Per risolvere questo problema si può usare il seguente algoritmo:

I. Leggi: la stringa

2. ripeti per ogni carattere della stringa:

2.1. se il carattere è compreso tra A ed Y

allora: sostituiscilo con la lettera successiva;

altrimenti: se il carattere è la lettera Z:

allora: sostituiscilo con la lettera A;

altrimenti: lascia il carattere inalterato

in corrispondenza a ciascuna delle seguenti frasi di assegnazione:

AUGURI = 'BUONvNATALEvEvFELICEvANNOvNUOVO'AUGURI = 'BUONvI987'

AUGURI = 'TANTIvAUGURlvDIvBUONvCOMPLEANNO'

Indicare il contenuto delle sottostringhe

AUGURI (: 4)

AUGURI (5 : 12)

AUGURI (7 : 12)

AUGURI (16 : 17)

AUGURI (21 : 26)

AUGURI (27 :)

scrivere le frasi di assegnazione che permettono di:

a) assegnare a PRIMO la stringa di caratteri che si ottiene concatenandoi valori dei tre elementi del vettore LISTA:

b) sostituire all'ultimo carattere di PRIMO la lettera W;

c) sostituire il contenuto del primo elemento di LISTA con i primi cinquecaratteri di PRIMO;

d) sostituire il secondo carattere del secondo elemento di LISTA con il nu­mero 8.

n""" L

Esercizi

12.1 Indicare la lunghezza delle seguen ti costanti carattere:a) 'LAvVOLPEvARGENTATA'b) 'COSAv c"E"?' ìÒr

c) 'vQUESTA vAUTOMOBILE vE" vVELOCEv , ~

d) 'vROSSO, BIANCO. VERDEv I C,e) 'vvv'

12.2 Supponiamo che un programma contenga la seguente frase di specificazione:

CHARACTER * 31 AUGURI

12.3 Supponendo che un programma contenga la frase

CHARACfER * 5 LISTA (3), PRIMO * 15

12.4 Scrivere un programma che permetta dI copiare in ordine inverso in una va­

riabile carattere B i caratteri di un'altra variabile A, ovvero di sostituire l'ul­

timo carattere di B con il primo di A. il penultimo con il secondo e così via.

ha lo stesso valore di X

ha lo stesso valore di I

CHAR (lCHAR (X))

ICHAR (CHAR (I)

3. stop.

Nel programma seguente indichiamo con STR la stringa data e con L la sualunghezza che supporremo al più uguale ad 80.

PROGRAM ROTAZCHARACTER STR * 80, CAR, SREAD *, LREAD -. STRDO IO I=I,LCAR = STR (I : I)IF (A'.LE.CAR.AND.CAR.LE.'Y') THEN

S = CHAR(lCHAR (CAR) + I)ELSE IF (CAR.EQ.'Z') THEN

S= 'A'ELSE

S=CARENDIFSTR (I: I) = S

IO CONTINUEPRINT *, STRSTOPEND

riI

!.\

!!

I

Page 100: Fortran

192

12.5 Scrivere un programma che stampi in ordine alfabetico i cognomi di 25alunni di una classe.

12.6 Scrivere un programma che, data una stringa di 80 caratteri, ne costruiscaun'altra ottenuta dalla prima sopprimendo le spaziature.

12.7 Scrivere un programma che legga N righe di un testo ciascuna delle quali

è composta da 80 caratteri e contiene soltanto parole complete. Il program­

ma deve contare il numero di parole contenuto nelle N righe, il numero di

occorrenze della lettera A e di una stringa assegnata STRING.

Supponendo N = 7 e STRING = 'MODELLO', eseguire il programma aven­do come dato il testo seguente:

«Come è ben noto la ricerca della soluzione di molti problemi può esserespesso così schematizzata:

- si sostituisce al problema reale un modello matematico che conserva lecaratteristiche essenziali del problema di partenza;

- si sceglie il metodo per risolvere il modello in esame;

- si interpreta la soluzione trovata in termini del problema di partenza perverificarne la validità».

l

13Operazioni di ingresso / uscita con formato

13.1. Alcune considerazioni sulle frasi di ingresso/uscita guidate dalla lista

In generale, un'istruzione di ingresso/uscita deve contenere le seguenti indi­

cazioni: la direzione in cui avviene la trasmissione di informazioni, dall'esternoverso la memoria (ingresso) o dalla memoria verso l'esterno (uscita); il mezzo di

ingresso/uscita da~-;e; la lista delle locazioni di memoria interessate alla

trasmissione delle informazioni e le modalità secondo le quali tali informazioni

devono essere rappresentate all'esterno. Così, ad esempio, nelle frasi di ingres­

so/uscita guidate dalla lista

READ *, A, N

PRINT *, A, N

le parole chiave READ e PRINT indicano il tipo di operazione, 11 mezzo usato non

è esplicitamente indicato ed è quello standard, la lista A, N indica le locazioni di

memoria di cui si deve trasmettere il contenuto ed infine l'asterisco indica che le

modalità di rappresentazione esterna dei valori trasmessi dipendono dal sistema e

dalla lista (in questo senso va infatti interpretata la denominazione «guidate dalla

lista»).

Come si è accennato nel cap. 8, le frasi READ * e PRINT * sono molto sem­plici da usare ma poco flessibili perché non consentono di scegliere il modo in

cui i dati devono essere disposti sul mezzo di ingresso/uscita; ciò può implicare,

in un'operazione di lettura, l'impossibilità di usare insiemi di dati già predisposti

perché questi non possono essere interpretati nel modo desiderato.

Esempio 13.1. Consideriamo il seguente problema. supponendo che l'unità di

ingresso standard sia il lettore di schede. Per ogni dipendente di un'azienda si

ha una scheda già predisposta su cui sono perforati anno di nascita, nome e co­gnome, senza alcuna spaziatura fra il primo dato e il nome ma con uno spazio

fra questo e il cognome. Si vogliono leggere le schede una per volta memorizzando

l'anno di nascita in una variabile intera, NASC, ed il nome e cognome in una va­

riabile carattere, NOME, di lunghezza 30. La frase di lettura

Page 101: Fortran

194

READ., NASC, NOME

non può essere usata allo scopo desiderato. Infatti, supponendo ad esempio cheuna scheda contenga i dati:

1928FRANCA GENSINI

essa viene così interpretata al momento dell'esecuzione della frase di lettura:

il primo dato è 1928FRANCA in quanto inizia con il primo carattere non blanke termina con il carattere che precede il blank successivo; il secondo dato è GEN­

SINI. Siccome il primo dato non è una costante intera e il secondo dato non è

una costante carattere, si crea una situazione di errore che impedisce la prosecu­zione del programma.

Come si vedrà nel corso del presente capitolo, in FORTRAN si possono usare

istruzioni di ingresso/uscita più generali di quelle guidate dalla lista, nelle quali è

possibile indicare esplicitamente una specificazione di formato, ossia una descrizio­

ne del modo in cui devono essere forniti e interpretati i dati (se si tratta di una

istruzione di ingresso) o in cui devono essere visualizzati i risultati (se si tratta di

un'istruzione di uscita). Le istruzioni di ingresso/uscita in F77 sono molto più

flessibili di quanto non lo fossero in F66. Le innovazioni portate rispetto allo

standard precedente sono sostanziali e numerose e pertanto, per rendere più sem­

plice l'esposizione di questo capitolo, si tralascerà di sottolinearle rimandando al­

l'appendice A2 per un riepilogo finale.

Nel seguito la sigla I/O (lnput/Output) potrà sostituire l'espressione ingresso/

uscita ed il termine record indicherà un insieme di caratteri rappresentato su un

qualsiasi supporto fisico quale, ad esempio, una riga di stampa, una scheda per!~

rata, una linea su video etc.

13.2. Specificazioni di formato

Le informazioni trasmesse durante un'operazione di I/O sono rappresentate

all'esterno della memoria su records. La struttura di tali records può essere descrit­

ta mediante una specificazrone di formato che, in particolare, individua una sud­

divisione di ciascun record in uno o più campi, ossia gruppi di caratteri ognuno

dei quali contiene un singolo dato; l'ampiezzadi un campo è il numero di carat­

teri che lo compongono. La specificazione di formato descrive completamente

il modo in cui ogni dato deve essere scritto nel campo che gli è destinato e può

inoltre contenere altre informazioni utili per l'interpretazione dei records.

Una specificazione dì formato ha la forma seguente:

r195

in cui ciascun e j può essere del tipo:

• r dr

• dor

• r sfdove:- r è uru;ontatoredi ripetizione che, se presente, deve essere una costante in-

tera positiva senza segno; r può essere omesso se uguale ad I;- d è un descrittore npettbile ossia una stringa di caratteri che specifica l'arn­pie;za del campo su ~ui deve essere rappresentata un'informazione, il tipo di

informazione ed il modo in cui essa deve essere scritta sul record;- d è un descrittorenon.ripetibile ossia una stringa di caratteri che fornisce alor ..u u_ . • •

compilatore particolari informazioni sulla composizione e l'interpretazione dì un

record;- sf è a sua volta una specifi~aziQnedif!!!J11 ato.

Ciascun e. della forma rdr equivale ad r descrittori dr separati da virgole;l

così per esempio,

(et' 2 dr' e3 ) equivale a (et, dr' dr' e 3)

Ciascun e. della forma rSf equivale ad una specificazione di formato costituitaI .

da r ripetizioni separate da virgole della specificazione di formato sf privata delle

parentesi; così, ad esempio, se sf indica la specificazione (e" ez),

(e" 2 sf' e3) equivale a (e,. (e l , ez' e" ez), e3)

In fig. 13.1 è riportato l'elenco dei descrittori ripetibili previsti in F77 che pos­

sono essere suddivisi in descrittori di tipo numerico, carattere e logico in base

al tipo di informazione rappresenta bile nel campo da essi descritto. In ogni

Descrittori ripetibili Descrittori ripetibili Descrittori ripetibilidi tipo numerico di tipo logico di tipo carattere

Iw Lw AIW.m AwFW.dEW.dEw.dEcDW.dGW.dGw.dEc

Figura 13.1. Descrittori ripetibili in F77.

Page 102: Fortran

196197

descrittore, il simbolo W rappresenta una costante intera positiva senza segno che

indica l'ampiezza del campo individuato dal descrittore mentre la lettera I, F, E,

D, G, A, L indica il tipo di informazione contenuta nel campo (numerico per

I, F, E, D, G, carattere per A, logico per L). II significato dei simboli d, ed m

(costanti intere non negative e senza segno) e di c (costante intera positiva e

senza segno) sarà chiarito nei paragrafi successivi.

In fig. 13.2 è riportato l'elenco dei descrittori non ripetibili previsti in F77;

nella stessa figura accanto ad ogni descrittore viene brevemente riassunto il suo

significato.

Come verrà ulteriormente specificato nel § 13.9, ogni elemento della lista in

una frase di I/O nella quale è indicata una specificazione di formato è associato ad

un descrittore ripetibile; il descrittore stabilisce in che modo deve avvenire la

conversione del dato dalla sua rappresentazione interna in memoria come valore

dell'elemento della lista di l/O alla sua rappresentazione esterna sul record, o

viceversa. I descrittori non ripeti bili presenti nella specificazione di formato non

sono invece associati ad alcun elemento del1a lista di I/O.

Esempio 13.2. Sono esempi di specificazioni di formato i seguenti:

13.3. Rappresentazione dei dati numerici sui records di I/O

I numeri sono rappresentati sui records di I/O in base dieci mentre sono rappre­

sentati in memoria nel sistema di numerazione usato dall'elaboratore. Pertanto

l'ingresso/uscita di un dato numerico implica l'esecuzione di un algoritmo di

conversione da un sistema di numerazione ad un altro e l'eventuale troncamento

o arrotondamento del1a mantissa per i numeri reali (cfr. cap. 3).

Esponiamo in questo paragrafo alcune regole generali riguardanti la rappresen­

tazione esterna dei dati numerici sui records di l/O.

• In ingresso i caratteri blank nelle prime posizioni di un campo destinato al1a

rappresentazione di un dato numerico non sono significativi, mentre un campo

costituito da soli caratteri blank viene interpretato come zero. Gli eventuali ca-

~taITenoTànK-presenti nel campo dopo il primo carattere non blank possono essere

interpretati come zero oppure ignorati e l'interpretazione dipende, per i mezzi di

I/O standard, dal sistema di calcolo. Negli esempi che seguono, quando non sia

diversamente specificato, adotteremo la convenzione che tali caratteri blank

vengano interpretati come zero, coerentemente con la regola esistente al riguardo

in F66. Va osservato che in F77 è possibile stabilire nel1a specificazione di forma­

to l'interpretazione di tali caratteri sia per mezzi di I/O standard che per mezzi

non standard utilizzando i descrittori non ripetibili BN e BZ (cfr. § 13.15).

• In uscita i numeri vengono sempre scritti nelle posizioni più a destra del campo

loro riservato e sono eventualmente preceduti da caratteri blank : il segno precede

immediatamente il primo carattere non blank. II segno + è considerato in F77

opzionale e la sua presenza nei campi numerici in uscita dipende dal sistema; si

può comunque imporre una convenzione specifica al riguardo usando i descrit­

tori non ripetibili S, SP, SS (cfr. § 13.15). Negli esempi che seguono adotteremo

la convenzione di omettere tale segno.

• In uscita un campo destinato al1a rappresentazione di un numero viene riem­

pito di asterischi se, tolti i caratteri opzionali, il dato non può essere rappre­

sentato secondo le modalità dettate dal descrittore. Così. ad esempio, un campo

di ampiezza 2 destinato a contenere un numero intero viene riempito di asteri­

schi se il dato da rappresentare è - 12 che richiede tre caratteri; se però il dato da

(12,12, F5.3)

(EI3.6, F5.1, F5.1, F5.1)

«5X, EI3.6, 5X, EI3.6»

(IX, 13, (15, F8.1, 15, F8.1, 15, F8.1»

fine di un record

inserimento della stringahl ... hn su un record di uscita

salto di n caratteri

descrittori di tabulazione

termine dell'operazione se la lista di I/O è esaurita

interpretazione dei caratteri blank nei campinumerici su records di ingresso

gestione del segno + nei campi numericinei records di uscita

fattore di scala per valori numerici

Figura 13.2. Descrittori non ripetibili in F77.

nX

TnTLnTRn

BNBl

sP

sSPSS

(15, F8.1)

(A4)

(v SPECIFICAZIONEvDlvFORMATO')

(3X,'H =', D22.15,'N =', 14)

(212, F5.3) equivalente a

(EI3.6,3 F5.l) equivalente a

(2(5X, EI3.6» equivalente a

(IX, 13,3(15, F8.1» equivalente a

Page 103: Fortran

r198 J99

rappresentare è + 12, allora il campo sul record di uscita è riempito con la stringa

12 ed il segno + non viene riportato, qualunque sia la convenzione in atto al ri­

guardo.

13.4. 1\ descrittore Iw per dati di tipo intero

Il descrittore Iw individua un campo destinato alla rappresentazione di un dato

intero. Sia in ingresso che in uscita il dato è rappresentato sul record come costan­

te FORTRAN intera.

viene interpretato secondo la specificazione di formato precedente. i dati lettisono i numeri 121, 1235, 25000, O. 12549.

Se lo stesso record viene interpretato secondo la specificazione di formato

(1112)

i dati letti sono i numeri 12. II. 23, 52, 50, O, O, O, 1,25.49.

Osserviamo che sul record non c'è nessun carattere di separazione fra un dato

e l'altro: la suddivisione in campi dedotta dalla specificazione di formato è suffi­ciente per individuare la fine di un dato e l'inizio del successivo.

vv123 oppure v+ 123 oppure +v123

Esempio 13.3. Su un record di ingresso un campo è individuato dal descrittore

15. Se il contenuto del campo è

esso viene interpretato come il numero intero 123. Se invece il contenuto del

campo è

Esempio 13.4. Indichiamo qui di seguito come II numero 333 puo essere rappre­

sentato su records di ingresso o di uscita in campi individuati da alcuni descrit­

tori lw.

13.5. I descrittori Fw.d, Ew.d, DW.d per dati di tipo reale e doppia precisione

Un descrittore Fw.d, Ew.D o Dw.d individua un campo di ampiezza w desti­

nato alla rappresentazione esterna di un numero reale. I descrittori Fw.d, Ew.d,

Dw.d, insieme a Ew.dEc, GW.d e Gw.dEc (cfr. § 13.15) saranno indicati con iltermine descrittori reali.

I descrittori reali in ingresso

In ingresso i descrittori reali sono tutti equivalenti : il dato può essere rappre­

sentato, nel campo di ampiezza w, nella forma di costante FORTRAN intera,

reale o doppia precisione. Se il dato è nella forma di costante reale con espo­

nente, l'esponente può essere scritto come una costante intera con segno non

preceduta dalla lettera E oppure D. Se nel campo è presente il punto decimale.allora il l'alare di d specificato nel descrittore non ha alcun significato; in caso

contrario, il dato viene interpretato come se fosse presente un punto decimale

immediatamente precedente le d cifre più a destra nella stringa di caratteri cherappresenta il numero, escluso l'esponente.

Esempio 13.6. Riportiamo qui di seguito \'interpretazione che viene data del

.contenuto di un campo di ampiezza 5 in corrispondenza a diversi descrittori, reali.

Campo Descrittore Interpretazione

uscita

**

333

v333

ingresso

333

v333

impossibile

(13,14,315)

descri ttore

1314

12

Esempio 13.5. La specificazione di formato

vl23v oppure + 123v

esso viene interpretato come il numero intero 123 o 1230 a seconda della con­

venzione in atto sull'interpretazione dei caratteri blank.

, I

Ii,l'

Il

III

è equivalente a

(13,14,15,15,15)

e descrive cinque campi consecutivi destinati alla rappresentazione di dati interi.

Il primo campo ha ampiezza 3, il secondo 4 e gli ultimi tre hanno tutti ampiezza5. Se il record di ingresso

121123525000 vvvv v 12549

vv2.5

2 .5vv

- 2 .5 v

. 2EO I

.7E-3

3 . 1+4

\vv3 vv

F5.0

F5.2

F5.4

F5.2

E5.l

05.1F5.2

2.5

2.5

- 2.5

2.

0.0007

31000.

3. se ogni spazio equivale ad uno zero oppure

0.03 se gli spazi sono ignorati.

Page 104: Fortran

200 201

dove lo zero prima del punto decimale può non essere presente, e dove:• al'" ad sono le prime d cifre della mantissa del numero espresso in base

dieci, e la cifra ad è ottenuta per arrotondamento;

• exp è una stringa di 4 caratteri che contiene la caratteristica b del numero

espresso in base dieci. In fig. 13.3 dove bI' b2, b3 rappresentano le cifre di b, si

riportano le forme di exp che si possono avere con il descrittore EW.d quando b

è compreso in valore assoluto fra O e 999; la scelta tra la forma in cui compare la

lettera E e l'altra forma dipende dal sistema. Se si usa il descrittore DW.d sono

possibili, a scelta del sistema, tutte le forme previste in fig. 13.3 e una terza forma

in cui la lettera D sostituisce la lettera E.

del punto decimale, resta disponibile un solo carattere per la parte intera del nu­

mero che invece è costituita dalle due cifre I e 2. Si osservi inoltre che medianteil descrittore F5.3 il numero 0.0004 viene rappresentato come zero mentre ilvalore 0.0005 è rappresentato come .00 l. Nel primo caso quindi il descrittore

non permette una corretta rappresentazione esterna del dato il cui valore sembraessere zero, mentre nel secondo caso si ottiene una rappresentazione dello stesso

ordine di grandezza del valore in memoria.

I descrittori Ew.J e DW.d in uscita

In un campo individuato dal descrittore FW.d su un record di uscita sono rap­

presentati come zero tutti i numeri reali che sono, in valore assoluto, minori di

0.5 x 10- d. Pertanto non conviene usare tale descrittore se si desidera che la

rappresentazione esterna di qualunque numero reale contenga informazioni sul

suo ordine di grandezza. In tal caso si possono usare i descrittori EW.d e Dw.d,

con w ~ d + 7, ai quali corrisponde una rappresentazione esterna della forma

Nell'ultimo caso si vede come, in corrispondenza dello stesso descrittore reale,

una stessa stringa di caratteri senza il punto decimale può essere interpretata in

modi diversi. Per evitare interpretazioni diverse da quella desiderata, è consiglia­

bile inserire sempre il punto decimale nei dati reali.

AI momento della sua acquisizione, il dato scritto nel campo in ingresso viene

letto e convertito nel sistema di numerazione usato dall'elaboratore' la sua rap-I . '

( . presentazione interna sarà in precisione semplice o doppia coerentemente con iii

l I \ tipo della locazione di memoria in cui esso deve essere memorizzato, e indipen~

dentemente dal numero di cifre decimali con cui esso è rappresentato sul record.

l descrittori reali in uscita

!II uscita i descrittori reali non sono fra loro equivqlenti in quanto definisco­

no modalità diverse di rappresentazione esterna di un numero reale nel campo

di ampiezza w. In ogni caso, indipendentemente dal tipo di rappresentazione

interna del dato (semplice o doppia precisione), la sua rappresentazione esternacontiene d cifre dopo il punto decimale di cui l'ultima ottenuta per arrotonda­mento.

II descrittore Fw.d in uscita

Il descrittore Fw.d produce in uscita la rappresentazione del dato nella for­

ma di costante reale FORTRAN senza esponente con d cifre dopo il punto deci­

male. Se il valore assoluto del dato è minore di l, la presenza o meno di uno zero

prima del punto decimale dipende dalla convenzione usata dal sistema di calcolo.Nel seguito adotteremo la convenzione di omettere questo zero.

Esempio 11.7. Riportiamo la rappresentazione esterna di arcuru numeri reali incorrispondenza a diversi descrittori Fw.d

(13.1 ) ± O.al ... ad exp

Rappresentazione Descrittore Rappresentazioneinterna esterna

fI (- 12.388) F6.3 ******fI (T2.388) F6.3 12.388fI (- 786.3346) FIO.3 V'V'-786.335fI (- 786.3346) F5.0 -786.fI (0.0004) F5.3 V'.OOOfl (0.0005) F5.3 V'.001

Si osservi che nel primo caso il campo, di ampiezza 6, viene riempito di aste­

rischi; infatti, essendo d = 3 ed essendo obbligatoria la presenza del segno - e

b exp

b=O E +00 oppure +000

l <lbl~9 E ± Ob, oppure ± OOb l

9 <Ibl ~99 E ± bi b2 oppure ± os,b2

99 <I bl~999 ± bi b2 b3

Figura 13.3. Forme di exp nella rappresentazione esterna ± O.al ... ad expcorrispondente a Ew.d.

Osserviamo che i numeri reali la cui caratteristica b e, in valore assoluto, mag­

giore di 999 non possono essere rappresentati mediante i descrittori EW.d e DW.d

ma solo mediante opportuni descrittori EW.dEc e Dw.dEc (cfr. § 13.15).

Page 105: Fortran

202 r 203

Esempio 13.8. Riportiamo la rappresentazione esterna prodotta da alcuni descrit­

tori EW.d e DW.d in corrispondenza di determinati valori interni. Nei primi due

casi indichiamo tutte le possibilità, negli altri soltanto una.

I descrittori EW.d e Dw.d consentono di rappresentare in uscita i numeri reali

con un qualunque numero di cifre di mantissa. Evidentemente è sufficiente fissare

d ,ç t quando è noto che un dato non può avere più di t cifre di mantissa esatte;

una diversa scelta di d provocherebbe la rappresentazione di cifre non attendibili

in quanto sicuramente affette da errore.

'ii Si osservi che i descrittori Ew.d e Dw.d possono essere usati in F77indif~e~l\

Il rentemente qualunque sia la rappresentazione interna del dato. Se, nel sistema~con'cui si lavora, il descrittore Dw.dproduce una rappresentazione esterna in cui com­

pare la lettera D, allora esso può essere usato quando si vuole mettere in evidenza,

che il dato riprodotto sal record era rappresentato internamente in doppia pre­cisione.

i

l'; I

Rappresentazione

interna

Il r- 786.5936)

Il (- 786.5(36)

Il (0.0001)

Il (0.0009)

Il (- 10- 8)

Il (2 )( 1015)

Descrittore

E13.6

010.3

EIO.3

EIO.3

011.4

011.4

Rappresentazione

esterna

- 0.786594E + 03 opp. - 0.786594 + 003

- 0.7870 + 03 opp. - 0.787E + 03 opp. 0.787 + 003

v O.lOOE - 03

vO.900E - 03

- 0.10000 - 07

VO.2000D + 16

Essa individua due campi di ampiezza 13 destinati alla rappresentazione di due

numeri reali. Secondo tale specificazione Il numero complesso 3.35 - li può

essere rappresentato nel modo seguente

",,0.335000E + al - 0.200000E + al

mentre il numero complesso + 7i, con parte reale uguale a zero, è rappresentato.ad esempio, da

""O.OOOOOOE + 00 ""0.700000E + al

Osserviamo che la specificazione di formato e i records precedenti potrebbero

anche riguardare l'ingresso/uscita di due numeri reali; infatti l'interpretazione

data ai due valori trasmessi è diversa a seconda se i due descrittori reali sono asso­

ciati. tramite la lista di 110. a due locazioni reali o ad una complessa.

13.7. I descrittori ripetibili per dati di tipo carattere

Per n/o di stringhe di caratteri si può usare il descrittore ripetibile Aw, dove

w rappresenta, come al solito, l'ampiezza del campo. Le modalità di rappresenta­

zione esterna del dato dipendono dalla relazione che sussiste fra we la lunghezza

Q dell'elemento della lista di 110 associato al descrittore.

Il descrittore Aw in uscita

In uscita, se w ;;;. Q, la stringa di Qcaratteri viene posta nelle Qposizioni più a de­

stra del campo preceduta da w-Q caratteri blank , mentre se w < Qnel campo ven­

gono riprodotti i primi w caratteri della stringa.

Esempio 13.10. Sia CANE ""LUPO la stringa di caratteri che si vuole riprodurre

su un record di uscita: essa viene rappresentata tutta o in parte, a seconda del de­scrittore usato:

Il descrittore Aw in ingresso

In ingresso, se w ;;;. Q vengono convertiti e memorizzati gli Q caratteri più a

destra del campo; se invece è w < Q la stringa di caratteri presente nel campo, se­

guita da Q - w caratteri blank, viene memorizzata nella locazione corrispondente.

13.6. I descrittori ripetibili per dati di tipo complesso

Per la rappresentazione di un numero complesso su un record di 110 occorrono

due campi individuati da due descrittori reali non necessariamente uguali fra loro;

il primo campo è riservato alla rappresentazione esterna della parte reale del nu­

mero, il secondo a quella della parte immaginaria. Nella specificazione di formato

i due descrittori possono eventualmente essere separati da uno o più descrittori

non ripetibili. Da quanto detto segue che un numero complesso viene rappre­

sentato su un record di IlO come una coppia di numeri reali; ricordiamo a tale

proposito che quando si usa la frase di ingresso guidata dalla lista, i numeri com­

pIessi devono essere fomiti sotto forma di costante FORTRAN complessa, ossia

come coppia di costanti reali, separate da una virgola e racchiuse fra parentesi.

Esempio 13.9. Sia data la seguente specificazione di formato (2EI3.6J.

Descrittore

A4

A5

A9

Al2

Rappresentazione

CANE

CANE""

CANE ""LUPO

""""""CANE""LUPO

Page 106: Fortran

204

Esempio 13.11. Sia MESE una variabile carattere di lunghezza g, in cui si deve

memorizzare la stringa di caratteri presente in un campo individuato da un descrit­

tore Aw. Gli esempi seguenti mostrano l'effetto che si ottiene in corrispondenza

ad alcuni descrittori e campi in ingresso.

205

destinati alla rappresentazione di dati di tipo carattere e non hanno ampiezz~

presrabnua, mentre gli altri sono dedicati alla rappresentazione di numeri interi

ed hanno ampiezza 3. 11 record

PER 'V N = 125 'V K v V A LE : V'V 5 'V E'VM 'V VA LE: - 12

Descrittore Campo in ingresso

A8 GENNAIO v

A7 GENNAIO

A9 GENNAIOvv

Stringa memorizzata in MESE

GENNAIO v

GENNAIOv

ENNAIOvv

corrisponde alla specificazione data: il primo, il terzo ed il quinto campo hanno

in questo caso ampiezze rispettive 6, 8, IO. Anche il record

RIGA 'V'V l 'V COLONNA 'V'V IPIANO 'V'V l

E' evidente che quando w > Q, il dato in ingresso deve essere «allineato a de­

stra» nel campo per evitare che vadano «persi» nella lettura caratteri significativi.

Inoltre si può osservare che il valore assegnato a MESE nell'ultimo caso è diverso

da quello che le verrebbe attribuito con la frase di assegnazione

MESE = 'GENNAIO v"/

Tale frase infatti provocherebbe il troncamento a destra della stringa

'GENNAIOv'V' e la memorizzazione in MESE del valore 'GENNAIO 'V'.

fii

corrisponde alla specificazione data, e in questo caso il primo, il terzo ed il quinto

campo hanno ampiezze 4,8,5.

!Da quanto detto segue che quando un record viene letto o scritto sotto il con­

tr~.,di un~s-p,ecifica~ion.. e di formato un dato di tipo carattere viene rappresenta­to su di esso senza gli apici delimitatori che caratterizzano le costanti carattere;

ric~~i~mo che tali apici sono obbligatori se il record viene letto con una frase

READ*.---Come si è messo in evidenza in questo esempio, la lettura di dati di tipo carat­

tere sotto il controllo del descrittore A w può non essere equivalente all'assegna­

zione mentre tale equivalenza sussiste sempre quando la lettura è guidata dalla

lista (cfr. cap. 12). D'altra parte, la regola seguita nella lettura di dati di tipo

carattere è coerente con il fatto che in uscita essi vengono riprodotti nelle posi­

zioni più a destra del campo loro riservato.

II descrittore A

Per l'I/O di dati di tipo carattere si può usare anche il descrittore A in cui.non

compare l'ampiezza del campo; in questo caso il campo risulta di ampiezza Q,

dove Q è la lunghezza dell'elemento della lista di I/O di cui si tr;~metteil vàlore.11 descnttore A può essere molto utile per l'uscita di dati di tipo carattere, il

cui valore viene riprodotto per intero sul record di uscita; d'altra parte questo

i~ descrittore va usato con molta precauzione in specificazioni di formato relative

~ a frasi di ingresso.

Esempio 13.1 :l. La specificazione di formato

(3 (A, 13»

equivale a

(A. 13, A, 13, A, 13)

e descrive un record costituito da sei campi: il primo, il terzo ed il quinto sono

13.8. Istruzioni di ingresso/uscita con formato relative ai mezzi standard

Le più semplici frasi di I/O con formato relative ai mezzi standard hanno la

forma seguente:

READ f, lista-di-ingresso

PRINT f, lista-di-uscita

dove:

• READ, PRINT, lista-di-ingresso e lista-di-uscita hanno lo stesso significato

visto nei capitoli precedenti;

• f è un identificatore di formato che può essere:

- un * (in questo caso la frase è guidata dalla lista);

- l'etichetta di una frase FORMAT presente nella stessa unità di programma in

cui compare la frase di I/O;

- un'espressione carattere;

- un nome di variabile dimensionata carattere.

Istruzione FORMAT

L'istruzione FORMAT è una frase non eseguibile che ha la forma

n FORMAT SI

dove:

Page 107: Fortran

'd,

I

,

206

• FORMAT è la parola chiave che identifica la frase;• n è l'etichetta, obbligatoria, della frase;

• sf è una specificazione di formato che risulta associata a tutte le istruzionidi ingresso/uscita della stessa unità di programma in cui figura n come identifi­catore di formato.

Esempio 13.13. Con la coppia di istruzioni

READ 150, N, M. A, B150 FORMAT (215, 2FI0.0)

si associa alla frase di lettura READ la specificazione di formato (215, 2F l 0.0),secondo la quale i valori da assegnare a N, M, A, B devono essere forniti su un

record secondo le modalità imposte dai descrittori 15 per i primi due e F 10.0 pergli ultimi due.

Se la stessa frase FORMA T è associata alla frase

PRINT 150, N, M, A, B

la specificazione di formato in essa contenuta descrive la struttura del record, sulmezzo di uscita standard, su cui verranno rappresentati i valori di N, M, A, B.

E' importante osservare che nella stessa unità di programma più frasi di 110, possono fare riferimento ad una stessa istruzione FORMAT e che u~';' frase.

" FORM~T può s.tare in qualunque punto dell'unità di programma (cfr. appendìce] \Il A3); di solito SI usa raggruppare tutte le istruzioni FORMAT prima della END ii

in modo da migliorare la leggibilità dell'unità di programma.'i

Esempio 13.14. Nel seguente programma la frase READ e la frase PRINT fannoriferimento alla stessa frase FORMAT, di etichetta 100, che contiene la specifi­cazione di formato (2EI3.6).

READ 100, A, BA=A+1.B = B - 5.PRINT 100, A, BSTOP

100 FORMAT (2 EI3.6)END

Se il record letto con la frase READ è "-U t1''''' I (I (J r (;

;/ vvv- 2.vvvvvvv-\87.vvvvvvvv

quello prodotto dalla PRINT è il seguente:

- 0.1 OOOOOE + al - 0.920000E + 02

207

Espressioni carattere come identificatori di formato

Se l'identificatore di formato in una frase di I/O è una espressione carattere,il valore dell'espressione o una sua sottostringa deve costituire una specificazionedi formato al momento dell'esecuzione della frase. Se la specificazione di formato

è definita da una sottostringa essa può essere preceduta soltanto da caratteri blank

ma può essere seguita da qualsiasi altro carattere.

Esempio 13.15. Nella frase

READ '(215, 2FIO.0)', N, M, A. B

l'identificatore di formato è costituito dall' espressione carattere'(215, 2F 10.0)';

questa istruzione è allora equivalente alla coppia di istruzioni READ e FORMAT

dell'esempio 13.13.

Esempio 13.16. Siano A e B variabili carattere rispettivamente di lunghezza 2 e

5. Le tre istruzioni:

A = '(2'B = 'FS.3)'PRINT A Il B, XI, X2

hanno, sul record di uscita, lo stesso effetto della frase

PRINT '(2F5.3)', Xl, X2

in quanto il valore dell'espressione A // B è la specificazione di formato (2 F5.3).

Esempio 13.17. Se A e B sono variabili carattere di lunghezza 8, le istruzioni

A = 'vv(313, F'B = '5.3) GGMM'PRINT A II B, LA, LB. Le. XI

hanno, sul record di uscita, lo stesso effetto della frase

PRINT '(313, FS.3)', LA, LB. LC, Xl

Il valore dell'espressione A//B contiene infatti la sottostringa (313, FS.3) che,

essendo preceduta da caratteri blank, è riconosciuta ed utilizzata come specifica­

zione di formato.

Esempio 13.18. Sia N una variabile carattere di lunghezza l. Nella frase:

PRINT '('j/N/I'13)',LA. LB, LC

l'identificatore di formato è costituito da un'espressione carattere il cui valore è

Page 108: Fortran

208

ottenuto concatenando la costante '(' con il valore di N e con la costante '13)'.Pertanto, se al momento dell'esecuzione della frase PRINT il valore di N è '2',la frase equivale a

PRINT '(213)', LA, LB, LC

mentre, se N vale 'S', essa equivale a:

PRINT '(513)', LA, LB, LC

Da questo esempio si vede che, tramite un identificatore costituito da una espres­sione carattere, si può associare ad una frase di I/O una specificazione di formatovariabile.

Variabili dimensionate carattere come identificatori di formato

Se l'identificatore di formato in una frase di I/O è il nome di una variabile

dimensionata carattere, allora }an~pecificazione di formato è il risultato della con­catenazione dei valori dei singoli elementi nell'ordine in cui essi son~-in~~~-ori~

oppure una sua sottostringa; in questo ultimo caso la specifica~io~e-d;··f~~~t~

può essere preceduta da caratteri blank e seguita da qualunque altro carattere.

Esempio 13.19. Consideriamo le seguenti istruzioni:

CHARACTER * 4 FORM(4)FORM(J) = '(313'FORM(2) = ')'READ FORM, Ix, Iy, Iz

La specificazione di formato associata alla frase READ è (313). Intatti conca­

tenando i valori dei quattro elementi di FORM si ottiene una stringa di 16 carat­

teri, in cui viene individuata la sottostringa (313) che costituisce appunto unaspecificazione di formato valida.

E' evidente che anche con identificatori di formato costituiti da variabili di­mensionate carattere si possono definire specificazioni di formato variabile nelsenso suggerito dall'esempio 13.18.

13.9. Interazione fra lista di ingresso/uscita e specificazione di formato

L'esecuzione di una frase di I/O con formato avviene scandendo insieme,da sinistra verso destra, la lista di I/O e la specificazione di formato. L'acquisi­

zione dei dati o la creazione dei records di uscita è contemporanea alla scansionedella lista e della specificazione di formato.

lj In quanto segue occorre tener presente che al momento dell'esecuzione di una

209

r:frase di I/0c:>gni nome di variabile dimensionata presente nella lista viene trattato I.I~

V~pome se fossero specificati tutti gli elementi della variabile nell'ordine in cu~V~

compaiono in memoria.

lnterazione lista-formato nelle operazioni di ingresso

Un'operazione di ingresso inizia con la trasmissione all'interno della memoria

del record che deve essere letto (record corrente). Successivamente inizia la scan­

sione della specificazione di formato.• Se, durante la scansione della specificazione di formato, si incontra un descrit­

Itore ripetibile che definisce un campo di ampiezza w SI controlla se è già statoI

~.letto ed assegnato un valore a tutti gli elementi della lista. In caso affermativo, I )( 'I i:l'operazione di ingresso ha termine; altrimenti essa prosegue con l'acquisizione , I J \ .

I: ,! !di un dato dal record corrente ossia viene letta una stringa di w caratteri che, in- ( !l/tI ~ " terpretata in base al tipo del descrittore, costituisce il valore da assegnare al primo '..' t\: ,l~id

\ elemento della lista di ingresso il cui contenuto non è stato ancora definito. In: i; IJ ,;

corrispondenza ad un elemento della lista di tipo complesso la scansione della spe- !Ii J

cificazione di formato procede fino ad incontrare un altro descrittore ripetibile Ie, dal record corrente, si leggono due campi.Il procedimento ora descritto può essere realizzato correttamente soltanto se il

dato sul record di ingresso è nella forma prevista dal descrittore e se quest'ultimoè del tipo opportuno in relazione al tipo dell'elemento della lista di ingresso (cfr.

fig. 13.4). Tutte le situazioni che impediscono il corretto svolgimento della ope­razione provocano l'interruzione dell'intero programma a meno che esse non ven-

Tipo dell'elemento Tipo del descrittorenella lista di I/O ripetibile

intero intero: lw'llw.m / '7~G /' (

reale reale: Fw.d, Dw.d,Ew.d, EW.dEc

doppia precisione Gw.d, GW.dEc

complesso una coppia di descrittori reali

carattere carattere: A, Aw

logico logico: Lw

Figura 13.4. Corrispondenza tra il tipo degli elementi deUa lista di I/O e queUo dei descrittoriripetìbili.

Page 109: Fortran

210 211

sia disponibile sull'unità di ingresso il seguente record:

v- 0.2,vO.2v,2l5

READ '(2F5.l, 13)', A, B, N

impone la lettura di due numeri reali da memorizzare in X e Y; i dati devono es­

sere scritti su un unico record secondo la specificazione di formato (SFI0.3),

ossia (FIO.3, FIO.3, FlO.3, FIO.3, FI0.3). Ai primi due descrittori ripetibili

F I0.3 vengono associati gli elementi X, Y della lista di ingresso ai quali vengono

quindi assegnati i valori risultanti dall'interpretazione e conversione delle stringhe

presenti nel primo e nel secondo campo rispettivamente. Quando viene incontrato

il terzo descrittore F I0.3 l'operazione termina perché è terminata la scansionedeBi"Usta di ingresso.--------._--- -

A; pertanto la stringa v -0.2 presente nel primo campo di ampiezza S viene inter­

pretata come numero reale -0.2, viene convertita nella rappresentazione internafl( - 0.2) e memorizzata in A;

• il secondo descrittore incontrato è ancora un descrittore ripetibile FS.I ; al se­

condo elemento della lista di ingresso B, viene assegnato il valore fl(0.2) risultan­

te dall'interpretazione e conversione della stringa vO.2 v presente nel secondocampo del record;

• il terzo descrittore incontrato è il descrittore ripetibile 13 e il terzo elemento

della lista è la variabile intera N; la stringa 21S presente nel terzo campo viene al­lora interpretata come un numero intero che viene assegnato ad N;

• viene incontrata la parentesi finale della specificazione di formato ed essendoormai stato assegnato un valore ad ogni elemento della lista di ingresso, l'opera­zione ha termine.

Esempio 13.23. L'esecuzione della frase

READ '(F8.\, 2(13, FIO.O))', A. N, B, NM. BM, K, BK

Esempio 13.22. La frase

READ '(5FI0.3)', X, Y

avviene nel modo seguente. Dal primo record vengono letti, secondo la specifi­

cazione di formato (F8.I, (13, F 10.0, 13, F 10.0)), cinque valori che vengono

assegnati nell'ordine ad A, N, B, NM, BM. A questo punto si incontra la parentesi

chiusa finale; si inizia allora la lettura di un nuovo record per acquisire i valori da

assegnare a K e BK. Su questo secondo record i dati vengono interpretati secondo

la specificazione di formato che inizia dal punto di riscansione, ovvero essi devonoaccordarsi con la specificazione (13, FIO.O, 13, FIO.O).

(13, (A3, 12, A3, 12), F5.3)

(13, «A3, 15, A3, 15), F5.3, (A3, 15, A3, 15),F5.3))

«A3, 12, A3, 12), (F5.3, 12, F5.3, 12))

(13, A3, A3, 12, 12)

«13, A3, 13, A3), 12)

(13, (A3, 12, A3, 12))

(13, 2A3, 212),(13, 2(A3, 12))

t(2(13, A3), 12)t

(13, 1(A3, 12), F5.3)

(2(A3, 12), rF5.3, 12))

(13, 2(2(A3, 15), F5.3))t

Esempio 13.21. Supponiamo che al momento dell'esecuzione della frase

Esempio 13.20. Nelle seguenti specificazioni di formato la freccia indica il punto

di riscansione; per maggior chiarezza, accanto a ciascuna specificazione viene indi­

cata la forma ad essa equivalente.

gano opportunamente trattate come indicato nel cap. 18.• Se, durante la scansione della specificazione di formato, viene incontrato un de­

scrittore non ripetibile viene eseguita l'azione da esso descritta e la scansione della

specificazione di formato procede con l'esame del successivo descrittore.

• Quando, durante la scansione della specificazione di formato. si incontra la

parentesi chiusa finale, l'operazione di ingresso termina se la sua esecuzione ha

permesso di definire il contenuto di tutti gli elementi della lista. In caso contrario,'

,I 1\ l'acquisizione dei dati prosegue dal record che, sull'unità di ingresso, segue imrne­I diatamente il record corrente; questo nuovo record viene trasferito in memoria

i \ e sostituisce il record corrente. La scansione della specificazione di formato ri-tIl ) .. I,. '

\ ~~e~de a partire dal punto di riscansione che coincide con l'inizio .della specifi, \ ì~ (' . caiìone di formato se questa no~ contiene specificazioni di formato interne; at-

(li I trimenti esso coincide con l'inizio della specificazione di formato che si chiudecon l'ultima parentesi interna destra.

i l'..l'

Esempio 13.24. Sia IND un vettore di IO elementi; \'istruzioneConsiderando che la specificazione di formato (2F5.l, 13) è equivalente a(F5.1, FS.I, 13), l'operazione di lettura avviene nel modo seguente:

• inizia la scansione della specificazione di formato. Il primo descrittore è il de­scrittore ripetibile FS.I e il primo elemento nella lista di ingresso è la variabile

'Il,READ '(14)', IND il

prevede di leggere un valore per ognuno degli elementi di IND secondo la speci-

II

I

Page 110: Fortran

212

ficazione di formato (14); siccome questa specificazione prevede un unico campo

di 4 caratteri, i valori delle lO componenti di IND devono essere scritti ognuno

nelle prime 4 posizioni di un record, per un totale di lO records successivi. I dati

devono invece essere fomiti su un unico record, in lO campi consecutivi di am­

piezza 4, se si usa la frase

READ '(1014)', IND

Supponendo infine che i dati vengano acquisiti con l'istruzione

READ '(414)', IND

devono essere predisposti 3 records distinti: il primo deve contenere i valori di

IND(I), IND(2), IND(3), IND(4), il secondo quelli di IND(5), IND(b), IND(7),

IND(8) e infine il terzo quelli di IND(9) e IND(lO). Ogni dato dovrà occupare

un campo di 4 caratteri.

Dagli esempi precedenti risulta evidente che il numero di records letti durante

una operazione di ingresso dipende dal numero di elementi della lista e dalla spe­

cificazione di formato; se il numero di records richiesti dall'operazione e maggiore

del numero di records disponibili sull'unità di ingresso, si crea una situazione di

errore che provoca la fine dell'esecuzione dell'intero programma a meno che essa

non sia prevista nei modi descritti nel cap. 18. In ogni caso occorre molta atten­

zione nel disporre i dati sui records di ingresso o nello scegliere la specificazione di

formato da associare ad una istruzione di lettura. A questo proposito si osservi

che una specificazione di formato deve essere tale da non imporre la lettura

di records più lunghi di quanto consentito dal supporto fisico su cui essi sono

rappresentati (sui mezzi di ingresso standard la lunghezza massima consentita

è di solito 80 caratteri).

Interazione lista-formato nelle operazioni di uscita

L'esecuzione di una frase di uscita con formato consiste nella creazione in me­

moria di uno o più records che successivamente vengono emessi sull'unità di usci­

ta. II numero e la struttura dei records creati dipendono dalla lista di uscita, dalla

specificazione di formato e dalla loro interazione. La scansione della lista e del

formato procede nello stesso modo visto per un'operazione di ingresso; in parti­

colare ogni volta che nella specificazione di formato si incontra un descrittore ri­

petibile, il valore dell'elemento della lista ad esso corrispondente viene convertito

e rappresentato sul record corrente secondo le modalità imposte dal descrittore.

Anche per le istruzioni di uscita deve essere rispettata la corrispondenza di tipo

fra elemento della lista di uscita e descrittore ripe tibile ad esso associato (cfr.

fig. 13.4). Inoltre, e buona regola evitare specificazioni di formato che diano luo-

l

213

go alla creazione di records troppo lunghi, ovvero costituiti da più caratteri di

quanti ne possono essere contenuti su una riga dell'unità di uscita prescelta (le

righe sulle usuali unità di uscita, come stampante, video, terminale, sono di so­

lito lunghe 80, 120 o 117 caratteri).

Esempio J3.25. Data la matrice intera MAT dichiarata con la frase

INTEGER MAT (3,2)

e data la variabile carattere N di lunghezza l, a cui si suppone assegnato il valore'3', l'esecuzione della frase

PRINT '('f/N//'I4)', MAT

determina la creazione di due records su ognuno dei quali vengono riprodotti i

contenuti degli elementi di una colonna di MAT secondo la specificazione di for­

mato (314). Ricordiamo infatti che la lista di uscita costituita dal nome di matriceMAT è equivalente alla lista:

MAT(I, I), MAT(2, I), MAT(3, I). MAT(I, 2), MAT(2, 2), MAT (3,2)

Così, se MAT contiene la matrice

(- 2)

5 15

-7 -3vengono creati i records seguenti:

vvv l vvv5 vv- 7

vv- 2 vv 15 vv- 3

Esempio J3.26. Supponendo che GG, MM, AA siano variabili intere contenenti

rispettivamente i valori 29, 6,49 l'esecuzione della frase

PRINT 1200, 'GIORNO:', GG, 'MESE:', MM, 'ANNO:', AA1200 FORMAT (3(A7, 13»

dà luogo alla creazione del record seguente:

GIORNO: V'29V' V' MESE: V'v6V' V' ANNO:V'49

Se la frase FORMAT fosse stata:

1200 FORMAT(A7,13)

allora si sarebbero ottenuti tre records di uscita:

GIORNO:v29

vV'MESE: vv6

vvANNO: v49

I

I

II,l'

lili

Il,I,lìI

Page 111: Fortran

Figura 13.5. Controllo della spaziatura verticale su stampante.

Esempio 13.27. Il record creato dalla frase PRINT dell'esempio 13.26 verrebbe

riprodotto su una riga della stampante privato del primo carattere. ossiaI

214

Osserviamo che per ottenere tre records distinti con la frase PRINT*, ossia senzaspecificazione di formato esplicita, si dovrebbero eseguire tre operazioni di uscita

distinte:

PRINT *, 'GIORNO:', GGPRINT -. 'MESE:', MMPRINT *, 'ANNO:', AA

Specificazioni di formato vuote

In F77 sono permesse istruzioni di I/O con specificazioni di formato vuote.

Se la specificazione di formato è vuota anche la lista deve esserlo. Sono quindi

ammesse le istruzioni seguenti:

REA D '()'

PRINT '( )'

L'effetto della prima frase è quello di ignorare il record corrente qualunque sia

il suo contenuto; quello della seconda è di creare un record vuoto.

Primo carattere

blank

o

+

Effetto

spaziatura singolo: il record vieneriprodotto sulla riga successivaall'ultima già stampata

spaziatura doppia: il record vieneriprodotto a distanza di una rigadall'ultima già stampata

solto di pagina: il record èriprodotto sulla prima rigadella pagina successiva

sovrastampa: il record èriprodotto sulla stessa rigadel precedente

215

I

II

,.

II

13.10. Controllo della spaziatura verticale su stampante

I records creati durante l'esecuzione di una frase di uscita possono essere

emessi sull'unità di uscita uno alla volta oppure tutti insieme, al termine dell'ope­

razione. Le modalità che regolano la gestione dei records di uscita dipendono dal

sistema e dalle unità usate e può essere anche prevista un'emissione «globale»

dei records di uscita nel senso che soltanto alla fine dell'esecuzione di un program­

ma vengono riprodotti sull'unità di uscita tutti i records creati da tutte le frasi

di uscita presenti nel programma stesso. In ogni caso ogni record viene riprodotto

a partire dal margine sinistro di una nuova linea sull'unità di uscita prescelta.

In generale, ogni sistema di calcolo prevede almeno una unità di uscita, che

chiameremo stampante, sulla quale è possibile controllare la spaziatura verticale

tra due linee di. uscita successive mediante opportune indicazioni nella specifi­cazione di formato. Infatti, quando il record viene emesso su stampante.. il suo

primo carattere non viene stampato ma viene usato per determinare la p~izlone'llldella riga su cui il record verrà stampato rispetto all'ultima riga già stampata ql: Ilrispetto all'inizio del foglio di stampa. Nella fig. 13.5 viene indicato l'effett~·che' ,

si ottiene quando il primo carattere è blank, O(zero), I, +; qualunque altro carat­

tere che si trovi nella posizione iniziale del record di uscita viene di solito conside­

rato come un carattere blank anche se in F77 non è stabilita alcuna norma al

riguardo.

IORNO:v29 vvMESE:vv6 vv ANNO:v49

Per evitare la perdita del primo carattere potremmo usare. ad esempio. la speci­ficazione di formato:

(A8, 13, 2(A7, 13»

Avendo aumentato di un carattere l'ampiezza del primo campo, la stringa

GIORNO: viene riprodotta nelle 7 posizioni più a destra del campo ed il primo

carattere del campo. che è anche il primo del record. è un hlank.

Il primo carattere del record di uscita su stampante può essere specificato

anche usando opportuni descrittori non ripetibili. come verrà specificato nelparagrafo successivo.

13.11. I principali descrittori non ripetibili

Il descrittore nX

Questo descrittore. in cui n è una costante intera positiva senza segno che non

può essere omessa neppure se uguale ad I, consente di spostarsi di n caratteri sul

record corrente. L'utilizzazione del descrittore nX permette quindi di ignorare

n caratteri su un record in ingresso o di creare un campo di n caratteri blank su

Page 112: Fortran

fii

I111

216

un record di uscita. Di solito questo descrittore viene usato nelle specificazioni

di formato associate a Istruzioni di uscita per spaziare opportunamente I risultatioppure per creare un blank come primo carattere del record. Ad esempio la speci­ficazione di formato

(IX, 3(A 7,13»

consente di non perdere il primo carattere nella stampa del record dell'esempio!13.26, ed ha quindi lo stesso effetto della specificazione indicata nell'esempio r13.27.

Esempio 13.28. L'esecuzione della frase

PRINT '(5X, 14, 5X, EI3.6)', N, X, M, Y

avviene nel modo seguente:

• il primo descrittore incontrato nella scansione di formato è 5X; allora sul re­cord di uscita vengono riempite con caratteri blank le prime 5 posizioni;

• il secondo descrittore è il descrittore ripetibile 14; ad esso viene associato il

primo elemento della lista di uscita, N, il cui valore viene riprodotto sul record

allineato a destra nel campo che va dalla sesta alla nona posizione;

• il terzo descrittore è ancora 5X; esso provoca l'inserimento di caratteri blanknelle posizioni dalla decima alla quattordicesima;

• il quarto descrittore, E13.6, è ripetibile e viene associato al secondo elementodella lista, X, il cui valore viene opportunamente riprodotto sul record su un cam­

po di ampiezza 13 a partire dalla quindicesima posizione;

• si incontra infine la parentesi finale e, siccome i valori di M e di Y devono essereancora riprodotti, la scansione della specificazione di formato riprende dall'inizio;

viene così creato un secondo record che ha la stessa struttura del primo, sul quale

sono rappresentati i valori di M ed Y.

I descrittori 'hl" . ho' e nHh l · · . ho

Durante un'operazione di uscita è possibile inserire sul record corrente una

stringa hl ... hn costituita da caratteri codificabili dal sistema mediante uno deidescri ttori:

'hl' .. hn ' ; nHh l··· hn

Il primo descrittore, non permesso in F66, ha la forma di una costante carattereed il secondo, disponibile anche in F66, è stato mantenuto per consentire che pro­

grammi scritti in F66 potessero essere eseguiti su elaboratori che realizzano il nuo­vo standard.

217

Esempio 13.29. Le istruzioni

PRINT 1000, RAGGIO, AREA1000 FORMAT (lX, 'RAGGIOv='. E13.6, 3X, 'AREAv=', E13.6)

permettono di visualizzare i valori delle variabili RAGGIO e AREA preceduti,

rispettivamente, dalle stringhe RAGGIO v = e AREA v =; se RAGGIO vale 2.

e AREA vale 12.5664, viene creato il record

vRAGGIOv= + 0.200000E + 01 vvv AREAv= + 0.125664E + 02

Si osservi che il carattere blank che precede la stringa RAGGIO v = e i tre blanks

che precedono la stringa AREA v = vengono creati sul record per effetto dei de­

scrittori IX e 3X rispettivamente.Lo stesso record può essere ottenuto con una delle seguenti coppie di istru­

zioni:

PRINT 1000, RAGGIO, AREA1000 FORMAT (lX. 8HRAGGIOv=, E13.6, 3X, 6HAREAV=, E13.6)

PRINT 1000, 'RAGGIOv=', RAGGIO, 'AREAV=', AREA1000 FORMAT (lX, A8, E13.6. 3X, A6, E13.6)

PRINT 1000, 'vRAGGIOv=', RAGGIO,'vvvAREAV=', AREA1000 FORMAT (2(A, EI3.6))

e con diverse altre combinazioni di specificazioni di formato e liste di uscita.

Esempio 13.30. Con le istruzioni

PRINT 20002000 FORMAT (vvPROBLEMAvTESTV')

si crea un record contenente la stringa di caratteri vvPROBLEMA vTEST v. Si

noti che la specificazione di formato non contiene descrittori ripetibili e che la

lista di uscita è vuota.

Se la stringa di caratteri che si vuole inserire in un record di uscita contiene un

apice, questo deve essere scritto come una coppia di apici consecutivi nel de­scrittore 'hl ... h

nI o come un solo apice nel descrittore nlfh, ... hn · Se poi

la specificazione di formato viene associata alla frase di uscita tramite un iden­tificatore costituito da una costante carattere, allora tutti gli apici devono esse­

re sostituiti da una coppia di apici consecutivi.

Esempio 13.31. Il messaggio 2vNONvE'v3 può essere stampato con varie com­

binazioni di frasi di uscita e specificazioni di formato, fra le quali:

Page 113: Fortran

218

PRlNT 2000. 2. 32000 FORMAT(lX, Il, IX, 'NONvE"v', Il)

PRINT '(IX, Il, IX, "NONvE""v", Il)', 2, 3

PRINT 2000, 2,32000 FORMAT (IX, Il, IX, 7HNONvE'v, Il)

PRlNT'(AlI )', '2vNONvE"v3'

PRINT '(A)', 'v2vNONvE"v3'

PRlNT'(IX, Il, A, Il)', 2, 'vNONvE"v',3

I descrittori 'hl ... h~ e nHh l· .. hn possono essere usati per ottenere comeprimo carattere di un record uno di quelli previsti in fig. 13.5. Così, ad esempio,il primo carattere del record creato con la frase

PRINT 555555 FORMAT (l', I5X, 'INIZI0vDELvFOGLIO')

è: l. Se il record viene emesso su stampante, esso viene riprodotto sulla prima rigadel foglio di stampa successivo, privato del primo carattere.

Il descrittore / (sbarra)

Una specificazione di formato può descrivere la struttura di più records siaquando viene riscandita più volte a causa della lunghezza della lista di I/O, siaquando contiene il descrittore non ripetibile [, Questo descrittore infatti indica

la fine della trasmissione di informazioni da (su) un record e l'inizio della tra­

smissione dal (sul) record successivo. In ingresso ciò significa che gli eventuali

caratteri non ancora letti sul record corrente vengono ignorati e, se la lista di in­

gresso prevede la lettura di altri dati, questi devono essere fomiti sul record suc­

cessivo. In uscita la sbarra fa sì che il record corrente venga considerato concluso

e che venga dato inizio alla creazione di un nuovo record. Osserviamo che in una

specificazione di formato si può omettere la virgola che precede un descrittoresbarra e quella che lo segue.

Esempio 13.32. L'istruzione

READ '(2FIO.3/214)', X, Y, I, J

indica che devono essere letti due numeri reali e due interi. La specificazione di

formato è tale per cui i dati devono essere fomiti su due records: il primo deve

contenere i valori reali da memorizzare in X e Y scritti secondo la specificazione

di formato (2FIO.3); il secondo deve corrispondere alla specificazione (214) edeve contenere i valon da assegnare a I e J. In altri termini, i dati devono esserefomiti come se fossero utilizzate le due istruzioni di lettura seguenti

READ '(2FIO.3)', X, YREAD '(214)', I, J

219

Esempio 13.33. Se VOTI è un vettore intero, l'esecuzione della frase

PRINT '(IX, "VETTORE vDEI v VOTI "/5(l X, 16»', VOTI

causa la creazione di un record che contiene il messaggio VETTOREvDElvVOTI

e di uno o più records successivi su ognuno dei quali sono rappresentati i valoridi cinque elementi di VOTI su campi di ampiezza 6 separati da un carattereblank. Il numero di records successivi al primo dipende dalla lunghezza di VOTI.Così ad esempio, se VOTI ha lunghezza 5 l'effetto della frase è quello di creareun solo record successivo al primo contenente i valori dei cinque elementi di

VOTI; se invece VOTI ha lunghezza 12 la frase provoca la creazione di tre recordssuccessivi al primo l'ultimo dei quali contiene due soli dati. Supponendo di voler

creare, dopo il primo, un record per ogni elemento di VOTI, si può usare la frase

PRINT '(IX, "VETTOREvDElvVOTI"/(lX, 16»', VOTI

nella cui specificazrone dI formato la coppia di parentesi interne serve ad impedire

la riproduzione della stringa VETTORE vDEI vVOTI su tutti i record successivial primo.

E' possibile distanziare tra loro le righe di stampa prodotte da una istruzione

di uscita inserendo nella relativa specificazione di formato più sbarre consecu­

tive. Infatti se durante la scansione della specificazione di formato si incontra

una sbarra l'operazione di uscita deve continuare sul record successivo. La scan­

sione del formato procede quindi con l'esame del successivo descrittore; se questo

è ancora una sbarra, il record corrente viene lasciato vuoto e l'operazione di uscitacontinua sul record successivo. Questo processo si ripete finché non si incontraun descrittore diverso dalla sbarra oppure la parentesi finale della specificazionedi formato. Ogni record lasciato vuoto viene riprodotto sul mezzo di uscita comeuna riga bianca. Così, eseguendo la frase

PRINT '(IX, 214///2(1 X, EI3.6»', N, M, A, B

si creano quattro records di cui il seconao ed 11 terzo VUOtI.

I3.12.La lista di ingresso/uscita

Una lista di I/O può contenerenomìdivarìabìle, nonudìelementì di variabile

dimensionata, nomi di variabile dimensionata e nomi di sottostringhe. Inoltre una

lista di uscita può contenere espressioni, eventualmente costituite da singole co­

stanti. Di una lista di l/O possono far parte elementi più complessi, detti liste conDO-implicito, che rappresentano in forma sintetica tutta la lista o parte di essa, e

che sono usate soprattutto in connessione con l'ingresso/uscita di variabili dimen­sionate.

Page 114: Fortran

220 221

PRINT *, (V(I), I = M, N)

oppure con la sequenza di istruzioni

DO 100, 1= M. NPRINT -. V(I)

100 CONTINUE

Si osservi che gli stessi valori vengono stampati nel primo caso con l'esecuzione

di una sola operazione e nel secondo caso con quella di N - M + 1 operazioni.

Volendo stampare i valori degli stessi elementi di V a gruppi di 3 su linee

successive, si può usare la frase:

PRINT '(3(1 X, E13.6»)', rvrn. l = M. N)

Esempio 13.36. Dato il vettore V specificato dalla frase

REAL V( - 20 : 20)

si vogliono visualizzare sull'unità di uscita standard i valori di V(M), V(M + 1),

..., V(N) dove M ed N sono noti e tali che - 20 ~ M ~ N ~ 20. Tale scopo può

essere ottenuto con l'istruzione

Lista con DO-implicito

Una lista con DO-implicito ha la forma seguente:

(5f' ,v = el

, e2

, e3

)dove:

• 5f' che diremo lista del DO-implicito. è una lista di ingresso o una lista diuscita coerentemente con il tipo di lista di cui la lista con DO-implicito fa parte;5f' può contenere a sua volta una o più liste con DO-implicito;

• v, el , e2, e3 hanno lo stesso significato dei simboli v, el, e

2, e

3visti nell'istru­

zione DO (cfr. cap. l O): v è detta variabile della lista con DO-implicito.

Al momento dell'esecuzione di una istruzione di I/O nella quale compareuna lista con D0-implicito, viene calcolato il contatore C in base ai valori delle

espressioni el , e2, e3 esattamente come se dovesse essere eseguita un'istruzione

del tipo DO n v = el' e2 , er La lista con DO-implicito è equivalente a quella otte­

nuta riscrivendo C volte consecutive la lista 5f'; ad ogni ripetizione di 5f' il valore

di v viene modificato come nella realizzazione di un ciclo-DO e di conseguenza

vengono modificati i nomi dipendenti da v che compaiono in .!f. Si può direquindi che 5f' costituisce il rango del DO-implicito.

Esempio 13.34. Le liste con DO-implicito seguenti equivalgono alle liste esplicitescritte accanto

(V(I), I = 1,4)

(A(I, J), J = 1, 3)

(X, Y, K = 1,5)

(N, ~ * N, N = 8,2, - 2)(U(I + 1), V(I - 1), I = 3, 1, - 1)

(K, W(K), K = 1,7,2)

V(l), V(2), V(3), V(4)

A(I, 1), A(I, 2), A(I, 3)

X,Y,X,Y,X,Y,X,Y,X,Y8, 2 * 8,6, 2 * 6,4, 2 * 4, 2, 2 * 2U(4), V(2), U(3), V(l), U(2), V(O)

1, W(l), 3, W(3), 5, W(5), 7, W(7)

Se la lista !f di un DO-implicito contiene a sua volta una lista con DO-implicito,

si ha una situazione di annidamento per la quale valgono le regole viste nel cap.

lO; in particolare le variabili di più viste con DO-implicito annidate devono essere

distinte.

Esempio 13.37. Data una matrice, MAT, l'istruzione

READ *, «MAT(I, J), I = l, N), J = l, M)

Esempio 13.35. Data la matrice reale AMAT dichiarata da

REAL AMAT (l4, 14)la sequenza di istruzioni

DO 100 I = l, 14PRINT '(5(5X, EI3.6»', (AMAT(I, J), J = l, 14)

100 CONTINUE

prevede la scrittura sull'unità di uscita standard di tutti gli elementi di AMAT.

Infatti per ogni valore che I assume durante l'esecuzione del ciclo-DO esplicito,la lista della frase PRINT è costituita dagli elementi AMAT (I, l), AMAT (I, 2),

..., AMAT (I, 14), ossia dagli elementi della l-esima riga di AMAT. Ciascuna riga

di AMAT viene quindi riprodotta su tre records contenenti rispettivamente i valori

degli elementi dal primo al quinto, dal sesto al decimo, e dall'undicesimo al quat­tordicesimo.

consente di acquisire N * M valori da attribuire agli elementi MAT(I, J) con

l ~ I ~ N e l ~ J ~ M. Gli stessi valori, nello stesso ordine, possono essere letti

con la sequenza di istruzioni

DO 100 J = l,MDO 100 1 = l, NREAD *, MAT(I, 1)

100 CONTINUE

in cui si effettuano N * M operazioni di lettura anziché una sola. In entrambi i

casi gli elementi MAT (I, J) vengono letti per colonne in quanto, per ogni valore

dell'indice di colonna J, viene fatto variare l'indice di riga l. Volendo stampare per

righe questi valori si può usare la frase

PRINT *, «MAT(I, J), J = l, M), I = l, N)

oppure la sequenza di istruzioni

l

Page 115: Fortran

222

DO 200 1= 1, NDO 200 J = l,MPRINT -, MAT(I, J)

200 CONTINUE

In quest'ultimo caso si ha la stampa di N * M linee ciascuna contenente un solo

valore.

13.13. Le frasi READ (u, f) e WRITE (u, f)

Le frasi READ e PRINT considerate fino ad ora consentono di effettuare le

operazioni di I/O esclusivamente sulle unità standard. Così, per esempio, se il

sistema utilizza come unità standard di ingresso e di uscita il terminale video, non

è possibile usare queste frasi per leggere dati da un lettore di schede o riprodurre

i risultati sul foglio di carta di una stampante.

Per usare mezzi di I/O diversi da quelli standard, è necessario ricorrere ad istru­

zioni di I/O nelle quali sia esplicitamente indicato quale mezzo di I/O deve essere

utilizzato.

A questo proposito si osservi che l'insieme dei records letti o scritti con una

istruzione di I/O del tipo visto fino ad ora costituisce un file esterno sequenzialela cui trasmissione avviene attraverso le unità di I/O standard. Infatti, come sarà

ulteriormente specificato nel cap. 18, un insieme di records costituiti da caratteri

interpretabili in base ad opportune specificazioni di formato è un file. Un file è

detto sequenziale se per accedere ad un suo record si deve scorrerlo tutto a par­

tire dal primo record, e viene detto esterno se contiene informazioni destinate ad

essere trasmesse mediante una qualunque unità di I/O.

Per individuare un qualunque file esterno si usa un numero intero non negativo

detto numero di unità, che consente anche di individuare il mezzo (unità) di I/O

che permette la trasmissione delle informazioni contenute nel file. In alcuni casi

la corrispondenza tra un file esterno, un numero di unità e un mezzo di I/O può

essere prestabilita dal sistema e in altri casi è possibile stabilirla mediante oppor­

tuni comandi dati al programma Iinker; in ogni caso tale corrispondenza può

essere stabilita nel programma tramite l'istruzione OPEN (cfr. cap. 18). E' possi­

bile specificare il file, e quindi l'unità di I/O interessati da un'operazione di I/O

usando come frase di ingresso la seguente:

READ (u, f) lista-di-ingresso

e, come frase di uscita, la seguente:

WRITE (u, f) lista-di-uscita

dove:

223

- READ e WRITE sono le parole che identificano le frasi;

• u è un'espressione intera il cui valore, al momento dell'esecuzione della frase,

rappresenta il numero di unità del file oggetto dell'operazione. Se l'operazioneavviene tramite l'unità standard u può essere un asterisco _;

• f è un identificatore di formato.

Esempio 13.38. Diamo alcuni esempi di istruzioni di ingresso sintatticamente cor­rette:

READ (5, '(1013)') MI, M2, M3

READ (IR, '(1013)') MI, M2, M3

READ(K + l, '(1013)') MI,M2,M3

READ(-, '(1013)') MI,M2,M3

READ (7,100), MI, M2, M3

100 FORMAT (1013)

L'esecuzione delle frasi READ (u, f) e WRITE (u, f) avviene allo stesso modo

di quella delle frasi READ f e PRINT f (cfr. § 13.9). Pertanto le istruzioni:

READ (-, f) lista-di-ingresso

WRITE (*, f) lista-di-uscita

sono equivalenti, nell'ordine, a:

READ f, Iista-di-ingresso

PRINT f, Iista-di-uscita

e le frasi:

READ r-, -) lista-di-ingresso

WRITE (-, -) lista-di -uscita

equivalgono alle frasi guidate dalla lista:

READ -, lista-di-ingresso

PRINT -, lista-di-uscita

13.14. Esempi di stampa di variabili dimensionate

Nel calcolo scientifico si presenta spesso la necessità di manipolare variabili

dimensionate di tipo numerico, a una o due dimensioni, e quindi di leggere e

stampare, tutti o in parte, i contenuti dei loro elementi. In generale la lettura

degli elementi di una variabile dimensionata non presenta particolari difficoltà,

Page 116: Fortran

224

una volta stabilito l'ordine in cui si vogliono far leggere i dati. La stampa invece

può presentare alcune difficoltà, soprattutto se si vuole che l'insieme dei dati

stampati sia facilmente leggibile ed interpretabile. E' evidente che l'istruzionedi uscita guidata dalla lista è in questo caso poco opportuna e che conviene invece

usare istruzioni di uscita che facciano riferimento ad una specificazione di forma­

to. Negli esempi che seguono si vuole mettere in luce quali siano le considerazioni

che generalmente possono essere fatte per stabilire una specificazione di formato

opportuna in base alla lista degli elementi che si devono stampare. In tutti gli

esempi supponiamo che la stampante sia identificata dal numero di unità 2 e che

le linee di stampa siano lunghe 80 caratteri.

Esempio 13.39. Vogliamo stampare i valori degli elementi di una matrice di tipo

intero il cui dichiaratore è MAT (0:7,20:27). Si vuole che tali valori siano stam­

pati per righe, una riga su ogni linea di stampa, e che siano preceduti dall'intesta­

zione

STAMPA DI MAT PER RIGHE

Scegliendo il descrittore Il O per la stampa di ciascun elemento, e considerando

che ciascuna riga di MAT è composta da 8 elementi, è possibile descrivere la

struttura di una linea di stampa corrispondente ad una riga di MAT con la specifi­

cazione di formato (81 lO) come mostrato nella figura seguente.

INTEGER MAT(0:7,20:27)

DOlO 1=0,700 IO J = 20,27MAT(I,J)=I.J

lO CONTINUEWRlTE (2, '(30X, "STAMPAvDlvMATvPERvRlGHE" 130X, 23 (" - ") Il

• (8110)') «MAT (I, J), J = 20,27), I = 0,7)

END

STAMPA DI MAT PER RIGHE

225

Esempio 13.40. Sia REL una matrice reale con M righe e N colonne, con N > S.

Si vogliono stampare gli elementi di REL per righe.Se si sceglie il descrittore E 13.6 per stampare ogni elemento e si decide di se­

parare ogni valore dal successivo con due caratteri blank, abbiamo un totale di15 caratteri occupati dalla rappresentazione del valore di ciascun elemento.

Pertanto, essendo ciascuna linea composta da 80 caratteri, potremo al più stam­

pare 5 valori per linea, e siccome si è supposto N > 5 saranno necessarie più linee

di stampa per riprodurre ciascuna riga di REL. Consideriamo i due casi seguenti:

a) N è un multiplo di 5; in tal caso ciascuna riga di REL può essere riprodotta

esattamente su N/S linee successive;b) N non è un multiplo di 5; in tal caso ciascuna riga di REL può essere ripro­

dotta su più linee, di cui l'ultima contenente meno di 5 valori.Nel caso a) la stampa di REL può essere effettuata con un'unica operazione;

in fig. 13.7 si tratteggia un programma relativo alla stampa di una matrice RELdi 3 righe e IO colonne e si riportano le linee di stampa ottenute. Nel caso b)

è conveniente eseguire tante operazioni di stampa quante sono le righe di REL;

in fig. 13.8 si riporta un esempio relativo ad una matrice REL di 3 righe e 12

colonne.

C STAMPA DI REL (M, N) CON N MULTIPLO DI 5PARAMETER (M = 3, N == lO)REAL REL (M, N)

DO lO I=I,MDO lO J=I,N

IO REL(l,J)=ld+0.005

WRITE (2, ISO) N/5, «REL(l, J), J = I, N ),1 = I, M )ISO FORMAT(l4X,'STAMPAVDIVRELVPERvRIGHE',12,

• 'LlNEEvPERvCIASCUNAvRIGA' Il 5 (2X, E13.6»)

END

STAMPA DI REL PER RIGHE, 2 LINEE PER CIASCUNA RIGA

Figura 13.7. Programma e stampa relativi al caso a) deU'esempio 13.40.

o o o o o o o20 21 22 23 24 25 2640 42 44 46 48 50 5260 63 66 69 72 75 7880 84 88 92 96 100 104

100 105 110 115 120 125 130120 126 132 138 144 150 156140 147 154 161 168 175 182

Figura 13.6. Programma e stampa relativi all'esempio 13.39.

o275481

108135162189

0.100500E+Ol0.600500E+010.200500E+Ol0.120050E+020.300500E+Ol0.180050E+02

0.200500E+010.700500E+Ol0.400500E+010.140050E+020.600500E+010.210050E+02

0.300500E+010.800500E+01O.G00500E+01O.lG0050E+02O.900S00E+01O.2400S0E+D2

D.4DDSDDE+D10.9DDSDDE+DlD.8DDSDDE+DlD.18DDSDE+D2D.12DDSDE+D2D.270DSOE+D2

D.SDDSDDE+D10.lDDDSDE+D2D.IDDDSDE+D2D.2DDDSDE+D2D.lSDDSDE+D2D.30DDSDE+D2

Page 117: Fortran

Il 226 227

Figura 13.8. Programma e stampa relativi al caso b) dell'esempio 13.40.

'('fICAR (Nl : Nl) Il '110)'

RIGA 10.100500E+01 0.200500E+01 0.300500E+01 0.400500E+01 0.500500E+010.600500E+01 0.700500E+01 0.800500E+01 0.900500E+01 0.100050E+020.110050E+02 0.120050E+02

RIGA 20.200500E+01 0.400500E+01 0.600500E+01 0.800500E+01 0.100050E+020.120050E+02 0.140050E+02 0.160050E+02 0.180050E+02 0.200050E+020.220050E+02 0.240050E+02

RIGA 30.300500E+01 0.600500E+01 0.900500E+01 0.120050E+02 0.150050E+020.180050E+02 0.210050E+02 0.240050E+02 0.270050E+02 0.300050E+020.330050E+02 0.360050E+02

D020 I = l,MIDO 20 J = I,NIINT (I, J) = I • J

20 CONTfNùE

WRITE (2, '('tICAR (NI : Nl)11 '110)') «INT(I, n. J = l. Nn.1 = I. MI)

END

Fipra 13.9. Propanma relativo ...·aempio 13.41.

C ESEMPIO DI UTILIZZO DI SPECIFICAZIONI DIC FORMATO VARIABILE

INTEGER INT (50,50)CHARACTER • 8 CARCAR = '12345678'

C LETTURA DI MI <; 50 E NI.;;; 80 'DREAD., MI, NlWRITE (2, 150) MI, NI

150 FORMAT(lOX, 'STAMPAvDELLAvSOTTOMATRICE (',12,','·12, ')VDIVINT, VPERvRIGHE')

STAMPA DELLA SOTTOMATRICE 5, 4) DI INT, PER RIGHE

1 2 3 42 4 6 83 6 9 124 8 12 165 lO 15 20

STAMPA DELLA SOTTOMATRICE 5. 6) DI INT, PER RIGHE

2 3 4 5 64 6 8 lO 126 9 12 15 188 12 16 20 24

lO 15 20 25 30

STAMPA DELLA SOTTOMATRICE 5. 8) DI INT. PER RIGHE

1 2 3 4 5 6 7 82 4 6 8 lO 12 14 163 6 9 12 15 18 21 244 8 12 16 20 24 28 325 lO 15 20 25 30 35 40

Figura 13.10. Esempi di stampe relative aD'esempio 13.41.

DO IO I=I,MDO IO J=I,NREL (I, J) = I • J + 0.005

STAMPA DI REL(M, N), CON N MAGGIORE DI 5E NON MULTIPLO DI 5PARAMETER (M = 3, N = 12)REAL REL (M, N)

END

WRITE (2,200) N/5 + IFORMAT(l4X, 'STAMPAVDIVRELVPERvRIGHE, ',12,

• 'LINEE vPERvCIASCUNA v RIGA'I/)DO 20. I = I. M

WRITE (2,150) I, (REL (I, J), J = I, N)CONTINUEFORMAT (IX, 'RIGA', I1/5(2X, EI3.6»

STAMPA DI REL PER RIGHE, 3 LINEE PER CIASCUNA RIGA

cc

Esempio 13.41. Data la matrice intera INT di SO righe e SO colonne, si voglionostampare per righe gli elementi INT (I, J), con l ~ I ~ M1 e 1~ J ~ N 1, dove

M1 e N1 sono assegnati. Se si sceglie il descrittore 110 per ogni elemento, si pos­

sono stampare al più 8 elementi per linea. Il programma tratteggiato in fig. 13.9

dimostra come si possono usare specificazioni di formato variabile (cfr. esempio13.18) per stampare su ogni linea esattamente N1 valori, se N1 è minore o ugualedi 8.

Nel programma ci serviamo dell'identificatore di formato costituito dall'espres­sione carattere

IO

200

":!t

I20

150

I

l

Page 118: Fortran

228229

dove CAR (N l : N l) è la sottostringa costituita dal carattere che in CAR occupa

la posizione Nl. Essendo CAR uguale a '12345678', il valore di CAR (NI : Nl)

è proprio il «numero intero» Nl. Così, se Nl vale 4, CAR (NI : Nl ) è uguale a

'4' e la specificazione di formato è equivalente a (4J l O), mentre se N l vale 8, essaequivale a (8110).

In fig. 13.10 si riportano le stampe ottenute con il programma di fig. 13.9per MI = 5 e N I = 4. 6 e 8 rispettivamente.

13.15. Altri descrittori

Il descrittore Iw.m

II descrittore ripetibile IW.m individua un campo destinato alla rappresenta-

li

lzione d. i un numero intero, ~ in i!1~~esso equivale a Iw. !~ .!:!~iJil !.·I dato viene )

. rappresenjatn nel campo di ampiezza w con almeno m cifre, di cui 1~ prime Yl:uali lia zero se il numero è composto da meno di m cifre. Così, ad esempio, se I, J, K I)'..... "'---'---~~'---'----'- .. J

\ valgono rispettivamente 3, 22 e 546, la frase--

Esempio 13.42. La rappresentazione del numero - 2 x 1015 che si ottiene con f'il descrittore EI1.3E3 è - 0.200E + 015, mentre lo stesso numero viene rap- ,

presentato come - 0.200E + 0015 se si usa il descrittore EI2.3E4.

I descrittori GW.d e GW.dEc

I descrittori ripetibili GW.d e GW.dEc sono descrittori reali e sono quindiequivalenti In Ingresso a tutti gli altri descrittori reali. In uscita essi si comportano

in modo diverso a seconda dell'ordine di grandezza del numero x che deve

essere rappresentato nel campo di ampiezza w.

Se Ix I< 0.1 oppure Ix I~ IOd, i descrittori Gw.d e Gw.dEc equivalgono a

Ew.d ed Ew.dEc rispettivamente.

Se l Oi-I ~ Ix I< l o', con O~ i ~ d, allora si ~ttiene u~a - rapprese~~Zi~~ iesterna uguale a quella prodotta da un descnttore Fw.d, con d - dIA

e 'ii = w - k, seguita da k caratteri blank, dove k = 4 per il descrittore Gw.d J\mentre k = c + 2 per il descrittore GW.dEc.

PRINT '(314.2)', I, J, K

produce il recordEsempio 13.43. Nella seguente tavola si riportano le rappresentazioni esterne

di alcuni numeri reali ottenute in corrispondenza di diversi descrittori F, E, G.

vv03 vv 22 v546.

w ~ d + c + 5.

E ± O... Obl·· . br

con (c - r) cifre zero prima di bl" Se Ib I~ IOc , il descrittore EW.dEc non può

essere usato e il campo viene riempito di asterischi. In ogni caso la rappresenta­zione (13.2) implica che deve essere

dove al'" ad ed exp hanno lo stesso significato loro attribuito nella rap­presentazione (13.1). Se la caratteristica b del dato in uscita è esprimibile, in

base dieci, come ± bi'" br ed è r ~ c (ossia Ib I< IOr , r ~ c), allora in (13.2)exp ha la forma seguente

RappresentazioneF12.5 E12.5 G12.5 G12.5E3

interna

f1 (243762.0) 243762.00000 vO.24376E + 06 vO.24376E+ 06 0.24376E + 006

f1 (-243762.0) ************ -0.24376E + 06 -0.24376E + 06 -.24376E + 006

f1 (-24376.2) -24376.20000 -0.24376E + 05 v-24376.vvvv -24376.vvvvv

f1 (-23.54) vvv-23.54000 -0.23540E + 02 v -23.540vvvv -23.540vvvvv

f1 (0.32693) vvvvvO.32693 v0.32693E + 00 vO.32693vvvv 0.32693vvvvv

f1 (0.021582) vvvvvO.02158 vO.21582E-01 vO.21582E-01 0.21582E -001

f1 (0.00021582) vvvvvo.ooozz vO.21582E-03 vO.21582E- 03 0.21582E - 003

± O.al ... ad exp( 13.2)

Il descrittore Ew.dEc

II descrittore ripetibile t:.w.dEc individua su un record di I/O un campo desti­

nato alla rappresentazione di un numero reale.!,!! ingresso, esso equivale a tutti

gli altri descrittori reali, mentre in uscita esso produceunà" rappresentazionedeldato, nel~~~'podiampiezza w, della forma

Page 119: Fortran

Quando, nella scansione di una specificazione di formato, si incontra il de­scrittore l'operazione di I/O ha termine se è stato trasmesso il valore di tutti

gli elementi della lista. Questo descrittore, che può non essere seguito e preceduto

da virgole, è utile essenzialmente per evitare che messaggi «non desiderati» venga­

no riprodotti sui records di uscita.

230

Il descrittore Lw

Il descrittore ripetibile Lw individua un campo di ampiezza w destinato alla

rappresentazione di un valore logico. In ingresso, il valore «vero» deve essere in

una delle forme T, . T , .TR VE. ed il valore «falso» in una delle forme F..F.

.F ALSE.; questi caratteri possono essere seguiti da qualunque altro caratt.ere -nei

campo di ampiezza w loro riservato. In uscita i valori «vero» e «falso» sono rap­

presentati rispettivamente dai caratteri T e F preceduti da w - l caratteri blank.

Il descrittore (due punti)

231

Ii

;1

I

~i[

I,

, I

i:

J descrittori Tn, TRn, TLn

l descrittori Tn, TRn, TLn sono chiamati descrittori di fabulazione in

quanto permettono di specificare, mediante la costante intera positiva senza

segno n che in essi compare, la posizione sul record corrente del successivo dato

da trasmettere. In particolare, il descrittore Tn indica che il campo relativo al

prossimo dato inizia con l'n-esimo carattere del record. Per spiegare invece

l'effetto dei descrittori TRn e TLn indichiamo con p la posizione sul record

corrente del carattere finale dell'ultimo campo utilizzato; il descrittore TRn

(TLn) indica allora che il campo destinato al prossimo dato inizia dalla posi­

zione p + l + n (p + l - n). In altre parole TRn e TLn specificano di quante

posizioni deve essere spostato, a destra e a sinistra rispettivamente, l'inizio del

campo successivo rispetto alla posizione (p + I)-esima. Il descrittore TRn è quin­

di equivalente ad nX mentre TLn è equivalente a TI se (p + l - n) ~ l.

Esempio 13.44. Se I è una variabile intera e CHAR una variabile carattere di lun­

ghezza 7, la frase

READ '(T5, 14, TL4, A7)', I, CHAR

viene così eseguita. Il descrittore T5 causa un salto al quinto carattere del re­

cord corrente; il descrittore 14 viene poi associato alla variabile I il cui valore

viene letto nel campo che va dal quinto all'ottavo carattere del record. Il descrit­

tore TL4 indica che il campo relativo al dato successivo inizia a partire dalla

Quinta posizione del record corrente in quanto si ha p = 8 e n = 4. Il descrittore

A7 viene poi associato alla variabile CHAR il cui valore viene letto nel campo che

va dal quinto all'undicesimo carattere del record. In questo modo i caratteri pre­

senti sul record nelle posizioni 5, 6, 7, 8 vengono letti due volte e vengono inter­

pretati nei due casi in modi completamente diversi. Se ad esempio il record lettoè composto dalla successione di caratteri

12341986/87ABCD

i valori assegnati alle variabili I e CHAR sono rispettivamente il numero intero

1986 e la stringa di caratteri 1986/87.

Esempio 13.45. Sia A un vettore reale i cui primi M elementi A(l), con l ~ I ~ M

ed M assegnato, sono definiti da A(l) = 2 • I + 0.5. Si vogliono stampare i sud­

detti elementi, facendo precedere il valore di ciascuno di essi dal suo nome A( I),

A(2), ecc.; inoltre il valore di un elemento deve essere separato dal nome del

successivo mediante una virgola.

Consideriamo a tale scopo la seguente istruzione dove si suppone che il numero

di unità 2 identifichi la stampante e che sia M ~ 99:

WRITE (2,3) M, (I, A(I), I = I, M)3 FORMAT (22X, 'STAMPAvDElvPRIMI', 12, 'vELEMENTIVDlvA'//

• 6 (IX, 'A(', 12, ') =', FS.! : '.')

Per effetto di tale frase vengono create una o più righe di stampa, ciascuna

contenente i valori di 6 elementi di A secondo il formato richiesto; osserviamo chela presenza del descrittore fra F5.1 e permette di non stampare la vir­

gola dopo il valore dell'ultimo elemento. Le righe di stampa contenenti i valori de­

gli elementi di A sono precedute da una riga in cui si segnala il numero di elementi

stampati. In fig. 13.11 si riportano le righe di stampa ottenute per M = 6 e M = IO

STAMPA DEI PRIMI 6 ELEMENTI DI A

Al 1)= 2.5. Al 2)= 4.5. Al 3)= 6.5, Al 4)= 8.5. Al 5)= 10.5. Al 6)= 12.5

STAMPA DEI PRIMI lO ELEMENTI DI A

Al 1)= 2.5. Al 2)= 4.5. Al )= 6.5. Al 4)= 8.5, Al 5)= 10.5. Al 6)= 12.5.Al 7)= 14.5. Al 8)= 16.5. Al 9)= 18.5. AllO}= 20.5

Figura 13.11. Stampe relative all'esempio 13.45.

J descrittori BN e BZ

I descrittori non ripetibili BN e BZ possono essere usati per stabilire una con­

venzione sull'interpretazione dei caratteri blank successivi al primo non blank

nei campi numerici dei records di ingresso (cfr. § 13.3). Più precisamente, se in

una specificazione di formato viene incontrato il descrittore BN o BZ tutti i blanks

presenti nelle posizioni suddette nei campi individuati dai successivi descrittori

Page 120: Fortran

232 233

Se il descrittore è Dw.d, Ew.d, oppure Ew.dEc, il valore di s deve soddisfare la re­

lazione - d < s";; d + l. Il campo prodotto in uscita se - d < s";; O ha la forma

seguente

Il descrittore sP

Il descrittore sP, dove s è una costante intera, specifica un fattore di scalache influisce sulle modalità di rappresentazione esterna dei numeri reali che

verranno trasmessi successivamente durante l'operazione di I/O. L'effetto di un

descrittore sP resta valido anche nel caso di riscansione della specificazione di

formato. In assenza di descrittori sP si intende che il fattore di scala è zero.

In ingresso un fattore di scala s diverso da zero influisce soltanto sull'interpre­

tazione dei numeri reali che sono scritti sul record in una forma senza esponente;

infatti se y è il numero scritto nel campo esso viene interpretato come y l O-s.

Per esemplificare quanto detto supponiamo di avere nel record di ingresso la strin­

ga 1525.; con la specificazione di formato (2P, FIO.O) la stringa viene interpretata

come il numero reale 1525.10- 2, ovvero 15.25, mentre con la specificazione

(- 2P, FIO.O) viene interpretata come 1525.10+ 2, ovvero 152500.

In uscita l'influenza di un fattore di scala diverso da zero varia a seconda del

descrittore ripetibile associato al campo su cui il numero reale deve essere rap­

presentato. Se il descrittore è Fw.d, allora il valore da scrivere nel campo è ot­

tenuto moltiplicando per 10s il numero che deriva dalla conversione in base dieci

del dato. Così, ad esempio, il valore - 4.3522 viene riprodotto come

di tipo numerico vengono ignorati o considerati zero rispettivamente. Ricordiamo

che in assenza di tali descrittori, i caratteri blank di cui stiamo trattando vengono

ignorati o considerati zero, a seconda della convenzione in atto per l'unità di in­

gresso usata (cfr. cap. 18). Osserviamo che l'effetto dei descrittori BN e BZ resta

valido anche quando la specificazione di formato viene nuovamente scandita. Ov­

viamente l'effetto di un descrittore BN viene annullato se, nel seguito della scan­sione, si incontra un descrittore BZ, e viceversa.

Esempio 13.46. Se il record

12 vvvvvv 0.5E2 vl2 vvvvvv 0.5E2

viene letto con la frase

READ '(BZ, 14, FIO.5, BN, 14, FIO.5)', I, A, J, B

i valori assegnati alle variabili I, A, J, B sono rispettivamente 1200, 0.5 x 102°,12, 0.5 x 102•

I descrittori S, SP, SS

l descrittori S, SP, SS possono essere usati in una specificazione di formato

relativa ad una istruzione di uscita per stabilire una convenzione riguardo alla

presenza o meno del segno + nella rappresentazione esterna dei numeri positivi.

In particolare, il descrittore SP indica che, in tutti i campi in cui deve essere rap­

presentato un numero positivo individuati dai successivi descrittori di tipo nume­

rico, deve essere presente il segno +; il descrittore SS indica che tale segno deve es­

sere omesso; infine il descrittore S indica che deve essere restaurata la convenzione

adottata dal sistema di calcolo. Lo standard F77 specifica che l'effetto di un

descrittore S, SP, SS resta valido anche in caso di riscansione della specificazionedi formato. (13.3)

vvv-4.3522

v-435.2200

vvvv-.0435

se la specificazione di formato è

se la specificazione di formato è

se la specificazione di formato è

(FIOA)

(2P, FIOA)

(- 2P, FIOA).

Esempio 13.47. Se le variabili LI, L2, L3 valgono rispettivamente 30, 31, 32,la frase

con k = Isi cifre uguali a zero dopo il punto decimale; se invece è O< s";; d + l,

allora il campo prodotto ha la forma seguente

PRINT '(IX, SP, 13, SS, 13, S,B)', LI, L2, L3(13.4)

determina la creazione del seguente record:

v+30v31v32

se il sistema prevede di non riprodurre il segno +; altrimenti si ottiene il record:

v + 30v3I+32.

l

In (13.3) e (13.4) exp ha una delle forme previste per i descrittori Ew.d,

Dw.d ed Ew.dEc. Le cifre ai e il valore dell'esponente b espresso in exp in (13.3)

e (13.4) vanno così interpretati: il valore espresso in base dieci del dato in memo­

ria è, a meno di arrotondamenti sull'ultima cifra decimale, ± 0.0 ... Dal a2 •••

ad - k x lOb e ± al" . as .as+ I ... ad+ 1 x IOb rispettivamente.

Page 121: Fortran

234 235

Esercizi

13.1. Individuare gli errori presenti nelle seguenti frasi:

READ '(3AIO)', CHAR (:10), CHAR (16:25), CHAR (26:)

READ '(5(A3, 13»', (CHAR (I : I + 2). LOC(I), I = 1,13,3).

vvlvv2vv3vv4vv5vv6vv7vv8vv9vvO

21 FORMAT (13, F8.1, 14)

13.2 Data l'istruzione FORMAT:

PRINT 234, N, «A(I. J), J = 1. N), I = l, N)

FORMAT (IX, 'NUMEROvDl vEQUAZIONI:'. 14//

IX, 'MATRICEvDELvSISTEMA:v'/5(2X, EI3.6»•234

13.5 Scrivere le liste di I/O che comprendono:

a) tutti gli elementi di un vettore V di lunghezza 30;

b) gli elementi di posto pari di un vettore v di lunghezza 30;

c) gli elementi della seconda colonna di una matrice, TAV, di 8 righe e I Ocolonne;

d) gli elementi di indici (1,1) di una matrice quadrata TAV con

N - M + l ~ I ~ N, N - M + I ~ J ~ N dove M < N;

e) gli elementi della I-esima riga di una matrice A di N righe ed N colonne.

13.4 Specificare Quanti records vengono prodotti con le seguenti istruzioni diuscita se N vale lO:

13.6 Scrivere una opportuna frase di ingresso/uscita guidata dalla lista per ognu­

na delle seguenti richieste:

a) leggere un valore di N e i primi N elementi del vettore V il cui dichiara­tore sia V(O : lO)

b) leggere un valore di N e la sottostringa costituita dagli ultimi N caratteridi una variabile carattere;

c) scrivere gli elementi della J-esima colonna di una matrice MAT ognuno

moltiplicato per il corrispondente indice di riga, supponendo che il dichia­ratore della matrice sia MAT ( IO, IO);

d) leggere le righe di ordine dispari di ciascun piano della variabile dimen­

sionata TRIO, il cui dichiaratore sia TRIO (9, IO, 4);

e) scrivere le potenze del 2 da 23 a 215 ;

f) leggere le righe di indici l, 4, 7, lO della matrice STR il cui dichiaratoresia STR (O: ro, O : 5);

g) scrivere in ordine inverso gli elementi di un vettore V il cui dichiaratoresia V(20).

13.7 Scrivere alcune possibili istruzioni che permettono di stam pare il messaggio

21, (N(I), X(I), M(I), I = l, lO)

21, N(I), X(5), M(7)

21, Kl

21, Kl, ALFA

21, (N(I), X(I), M(I), N(I + I), X(I + I), M(I + 1).1 = 2,9)

21, «L(I, 1), Y(I, 1), K(I, 1), I = l, ioi, J = l, lO).

READ

READ

READ

READ

READ

READ

READ., X, Y, X + Y

READ ., '(513)', N, M

READ '(214, 2E13.6)', X, Y, K, J

READ., (X, Y)

READ ., A(I), I = l, N

READ (6,77) «A(I, 1), I = l, N) J = l, N)

READ (6,77) «A(I, 1) I = I, N, J = l, N)

PRINT. X, Y, X + Y

PRINT (5, '(2 D22.15)') DI, D2

WRITE (5, '(2 D22.15)'), D L D2

PRINT '(1 X, G13.5)', (X .. 2, X = 1.5)PRINT, 250, X, Y

PRINT (., .) X, Y

WRITE (., 15) L +M

specificare quanti records vengono letti con ognunadelle seguenti frasi:

specificare il valore attribuito a ciascun elemento della lista delle seguenti

istruzioni di ingresso nell'ipotesi che i caratteri blank nei campi numericisiano interpretati come cifre zero:

13.3 Sia LOC un vettore intero di 30 elementi e CHAR una variabile carattere

di lunghezza 30. Supponendo di leggere il seguente record di ingresso:

READ '(1013)', (LOC(I), I = 1,30)

READ '(516)', (LOC(I), I = 1,30)

LAvSOLUZIONEvDELvPROBLEMAvE':v

supponendo che la stampante sia associata al numero di unità 6.

Page 122: Fortran

236

13.8 Scrivere una frase FO RMAT opportuna per ciascuna delle seguen ti istru­

zioni READ, in base alle descrizioni dei records specificate per ognuna diesse:

a) READ 1200, A, B, C, D

Ciascun record contiene nelle posizioni fra la Il-esima e la 20-esima com­

prese un numero reale in cui è presente un punto frazionario;

b) READ 1200, A, B, C, D, E, F, G, D

Ciascun record è composto da quattro campi di ampiezza 8; in ogni campo

è scritto un numero reale sotto forma di costante intera senza punto deci­

male, ed ogni numero è scritto nelle posizioni più a destra del campo.

13.9. Scrivere una frase FORMAT opportuna per ciascuna delle seguenti istru­zioni di uscita, in base alle descrizioni dei records specificate:a) WRlTE (5, 1300) A, B. C, D

I dati devono essere stampati m campi di ampiezza 20 nella forma senza

esponente con due cifre dopo il punto decimale. Ogni dato deve esserestampato su una riga a distanza di due righe dalla precedente;

b) WRITE (5, 1300) A, B, C, D

I dati devono essere scritti su una sola riga, ciascuno in un campo di ampiez­

za 13, nella forma con esponente con 6 cifre di mantissa. 11 primo datodeve essere preceduto dalla stringa di caratteri A = ~ , il secondo da B = ~ ,e così via:

c) WRlTE (5, 1400) I, U, K, V, W, J, Z, Y, X

I dati devono essere scritti su tre linee. La prima linea deve contenere i

primi due dati, la seconda i tre successivi e la terza gli ultimi quattro. Ogni

numero intero deve essere scritto in un campo di ampiezza 6, mentre ogni

numero reale deve essere scritto in un campo di ampiezza lO con esponente

e 3 cifre di mantissa. Due campi consecutivi devono essere separati da 3caratteri blank;

d) WRITE (5, 1500) I, J, (X(l), I = l, lO)

I primi due dati devono essere scritti su una riga in campi di ampiezza lO.

Deve poi seguire una riga contenente la stringa *** VETTORE~X *** apartire dalla Il-esima posizione. I successivi dati devono essere stampati 5

per riga, in campi consecutivi di ampiezza 20 separati da l carattere blank,nella forma con esponente con 13 cifre di mantissa.

237

13.10 Sia CAR una variabile dimensionata carattere, ogni elemento della quale

ha lunghezza 4. Scrivere una frase di uscita che permetta di stampare glielementi di CAR indicati dalla lista con DO-implicito

«CAR(I, 1), J = l, 8), I = l, 8)

su un «quadrato» così strutturato: ciascuna linea contiene 8 valori ognuno

separato dal successivo mediante 6 caratteri blank; fra una riga e l'altra ci

sono 3 linee vuote. L'intero quadrato deve essere preceduto dal titolo

QUADRATO~DI~LATO~8centrato rispetto al quadrato stesso.

13.11 Scrivere una frase di uscita che permetta di stampare la tavola pitagorica

da 5 a 9; gli elementi della tavola devono essere scritti in campi di ampiez­

za 3 e distanziati l'uno dall'altro mediante 2 caratteri blank. La tavola deve

essere preceduta dal titolo TAVOLA~PlTAGORICA~DA~5~A~9cen­

trato rispetto alla tavola stessa.

Page 123: Fortran

!i

illiIlII1

14Definizione e utilizzazionedei sottoprogrammi

14.1. Programma principale e sottoprogrammi

Nei capitoli precedenti è stata sottolineata la notevole utilità delle funzioni

intrinseche che permettono di eseguire operazioni non elementari di uso molto

comune. D'altra parte è possibile evidenziare diverse classi di problemi quali, ad

esempio, la risoluzione dei sistemi lineari algebrici o il calcolo degli autovalori

di una matrice la cui risoluzione è richiesta comunemente nelle applicazioni

scientifiche. Gli algoritmi risolutivi di questi problemi possono essere trascritti

in FORTRAN in modo da costituire unità di programma distinte dette sottopro­

C!~rrzmi che vengono autonomamente compilate e che, essendo identificate me­

diante nomi simbolici, possono essere utilizzate da qualunque programma. Per­

tanto, un programma FORTRAN è generalmente costituito da più unità: una

di esse, detta prozramma prinEipa/e. gestisce l'utilizzazione di tutte le altre e non

viene utilizzata da nessun'altra unità; le altre, i sottoprograrnmi, sono invece uti­

lizzate da una o più unità di programma e possono a loro volta utilizzare altri

sottoprogrammi. Per esemplificare, in modo semplice, quanto detto si consideri

l'esempio seguente:

Esempio 14.1. N studenti di un corso di laurea hanno sostenuto M esami ciascuno.

Si vuoI calcolare e stampare il voto medio riportato da ogni studente; inoltre, indi­

cata con mi la media con~eguita dall'i-esimo studente, si vuole calcolare e stampa-

re la media globale p. = (1: m.)/N.i= l I

Per risolvere questo problema si utilizza, evidentemente, il calcolo della media

aritmetica di un certo numero di valori noti. II procedimento per calcolare la me­

dia è infatti utilizzato N + I volte: le prime N per determinare il voto medio midi ciascuno studente, l'ultima per determinare la media globale p.. Indicate con vi'I ~ i ~ M, le votazioni riportate da ogni studente, un algoritmo risolutivo di que­

sto problema può essere formulato come mostra la fig. 14.1 nella quale l'algo­

ritmo 14.1 fa riferimento (N + 1) volte all'algoritmo 14.2 utilizzandolo, ogni vol­

ta, con dati diversi: quando serve per calcolare la media dei voti riportati da uno

Page 124: Fortran

240

Algoritmo 14.1

1. Leggi:M, N2. Per i = l, ..., N

2.1. Leggi: vl'·· ., vM2.2. Utilizza l'algontmo 14.2 per calcolare m.

3. Utilizza l'algoritmo 14.2 per calcolare Il. l

4. Scrivi: ml' .. " mN' Il.S. Stop

Algoritmo 14.2

1. Dati: n, al' ..., an2. Poni m =03. Peri= l, ..., n

l. Poni m = m + ai4. Poni m = m/nS. Risultato: m6. Stop

Figura 14.1. Algoritmo risolutivo deU'esempio 14.1.

studente, i suoi dati n, al' a2 , ... , an corrispondono, rispettivamente, al nu­

mero M degli esami ed alle votazioni vI' v2' ..., vM riportate; quando invece

esso è utilizzato per calcolare la media Il, allora deve usare come dati i valori

N, mI' m2, ..., mN" Per questo motivo, l'istruzione di lettura dei dati è sostituita

nell'algoritmo 14.2 da una frase che mette in evidenza soltanto quali e quanti

valori devono essere acquisiti mentre l'istruzione di scrittura è stata sostituita

da una frase che mette in evidenza il risultato fornito al termine dell'algoritmo.

La realizzazione in FORTRAN dei due algoritmi è il programma richiesto dal

problema; esso risulta costituito dalle istruzioni che traducono l'algoritmo 14.1 e

che costituiscono il programma principale e dalle istruzioni relative all'algoritmo14.2 che costituiscono il sottoprogramma.

Come è già stato accennato, ogni sottoprogramma può utilizzare più sottopro­

grammi e, a sua volta, può essere utilizzato da altre unità di programma. L'orga­nizzazione di un programma FORTRAN può essere pertanto molto complessa

e, in ogni caso, è sempre estremamente utile sapere come le diverse unità di pro­gramma interagiscono tra di loro. La composizione e l'organizzazione di un pro­gramma possono essere visualizzate graficamente mediante l'albero delle chiamate(1) che è costituito da più blocchi uniti da frecce: ciascun blocco rappresenta

(I) Questo nome deriva dalla consuetudine di indicare con chiamata di un sottoprogranuuala sua utilizzazione.

241

una unità di programma ed il nome dell'unità è specificato all'interno del blocco;se l'unità di programma chiama altre unità, il blocco che la rappresenta è unito a

tutti i blocchi che rappresentano le unità utilizzate mediante frecce dirette verso

l'unità chiamata. In fig. 14.2 è riportato un albero delle chiamate che mette inevidenza l'organizzazione di un programma costituito da otto unità di programma:un programma principale e sette sottoprogrammi. 11 programma principale utilizzail sottoprogramma NOME l il quale chiama tre sottoprogrammi: NOME2, NOME3e NOME4. Il sottoprogramma NOME2 chiama a sua volta NOME3 mentre l'unitàNOME4 utilizza i due sottoprogrammi NOME5 e NOME2. Infine, NOME5 utilizza

NOME 6 e NOME7 mentre NOME2 richiama NOME6.E' importante ricordare che il FORTRAN non è un linguaggio ricorsivo e, per-

1111 tant~ un sottoprogramma no.-!!.pyò richiamare se stesso in nes~~ ~llO_do, n~~i " .f(, attraverso l'utilizzazione di altri sottoprogrammi. Sono pertanto situazioni proibi- il i \ (

te quelle esemplificate in fig. 14.3. .

L'albero delle chiamate permette quindi di evidenziare quali e quante unitàdi programma devono essere disponibili per produrre il programma in forma

eseguibile. L'esecuzione del programma inizia sempre con quella del programmaprincipale. Ciascun sottoprogramma viene eseguito in corrispondenza di un'oppor­

tuna istruzione mediante la quale vengono fomite al sottoprogramma le informa­

zioni necessarie alla sua esecuzione. Il momento in cui si effettua lo scambio di

informazioni necessarie alla esecuzione di un sottoprogramma verrà detto (l!tiva­

~. del sottoprogramma e diremo invece uscita dal sottoprogramma il momentoin cui, terminata l'esecuzione del sottoprogramma, i risultati da esso ottenuti

sono disponibili per l'unità chiamante (detta anche unità attivante). L'esecuzione

di ogni unità di programma avviene quindi in modo sequenziale fino a che non si

incontra una frase che provoca l'attivazione di un sottoprogramma. Per effetto di

Figura 14.2. Esempio di albero delle chiamate.

Page 125: Fortran

242 243

INOME l H NOME 11la fine dell'esecuzione del sottoprogramma, il corpo del sottoprogramma eviden­ziato in fig. 14.4 dal blocco tratteggiato.

Figura 14.3. Esempi di situazioni ricorsive proibite in FORTRAN.

14.2. La prima istruzione di un sottoprogramma

Oltre alle funzioni intrinseche, in F77 sono previsti sottoprogrammi di tipo

SUBROUTINE, FUNCTION e BLOCK DATA che si distinguono mediante la

parola chiave specificata nella loro frase iniziale. In questa frase viene anche indi­

cato il nome che individua il sottoprogramma distinguendolo dalle altre unità che

costituiscono un programma. Un altro compito importante spesso riservato alla

prima frase di un sottoprogramma è quello di permettere lo scambio di informa­zioni con l'unità di programma chiamante. Questo scambio può infatti essere

realizzato mediante l'associazione di due liste di nomi: quella degli argomenti at­tuali, specificata nella frase che permette l'attivazione del sottoprogramma, e

quella degli argomenti muti specificata nella prima istruzione del sottoprogram­

ma. In generale diremo che un argomento muto ed un argomento attuale sono

associati quando identificano la stessa informazione. L'associazione tra le due li­

ste di argo~~~_~_a~i~n_~_~l momento dell'attivazione del sottoprogrammaquandoil primoa!gomento ~tt~~le_è associato al primo argomento muto, il secondo ar­

gomento attuale al secondo. argomento muto e così via fino all'ultimo argo­

mento attuiiie che-è asso~t;to alhìltlmo argomento muto. Facendo riferimento al­

IYesempÌo 14.] del paragrafo precedente, un sottoprogramma che calcola la media

m di n valori noti al' a2, ..., an basandosi sull'algoritmo ]4.2 deve iniziare con

una frase che ne specifica il nome e che può contenere, quali argomenti muti, i

nomi che identificano i dati n, al' ... , an ed il risultato m. L'attivazione di questo

sottoprogramma avverrà utilizzando in modo opportuno il suo nome e facendo

corrispondere alla lista degli argomenti muti quella degli argomenti attuali nella

quale devono essere specificati i nomi che identificano, nell'unità di programma

chiamante, gli effettivi valori di cui si vuoi calcolare la media. AI momento della

attivazione del sottoprogramma gli argomenti muti vengono associati a quelli at­

tuali ed il sottoprogramma viene pertanto eseguito usando come dati i valori iden­tificati dagli argomenti attuali.

Quanto detto mette in evidenza che una corretta utilizzazione di un sottopro­gramrna non può prescindere dalla conoscenza del significato degli argomenti

muti. In particolare useremo talvolta il termine argomento muto di ingresso per

mettere in evidenza il fatto che un argomento identifica una informazione tra­

smessa dall'unità di programma attivante al sottoprogramma; indicheremo invece

con il termine argomenti muti di uscita gli argomenti che identificano le informa­

zioni definite all'interno del sottoprogramma che vengono trasmesse in uscita al­

l'unità di programma chiamante. Evidentemente i risultati forniti da un sotto-

Unità di programmachiamata

Blocco diistruzioni

Blocco diistruzioni

Unità di programmochiamante

Riferimento al sottoprogramma

Figura 14.4. Trasferimento del controUo dell'esecuzione tra unità diprogramma chiamante e unità di programma chiamata.

questa frase il controllo dell'esecuzione è trasterito dall'unità attivante a quella at­

tivata fino al momento dell'uscita dal sottoprogramma quando l'unità chiamante

riprende il controllo dell'esecuzione. Quanto detto può essere sinteticamente sche­

matizzato come in fig. 14.4 dove il verso delle frecce indica il flusso di esecuzione

e istruzione di ritorno sta ad indicare una istruzione che determina la fine dell'e­

secuzione del sottoprogramma ed il trasferimento del controllo alla unità chia­

mante. Si osservi che, mentre la frase iniziale di un sottoprogramma è unica,

quella che determina il ritorno all'unità chiamante può non essere unica esatta­

mente come in un programma principale può non essere unica la frase STOP che

determina la fine della sua esecuzione. Le situazioni che determinano il ritorno

all'unità di programma chiamante sono descritte ne] blocco di istruzioni che

seguono la prima frase e che costituiscono, insieme con le frasi che determinano

Page 126: Fortran

244

programma fanno parte degli argomenti di uscita. Si osservi che un argomentopuò essere sia di ingresso che di uscita quando identifica una informazione che,trasmessa come dato dall'unità di programma attivante, viene poi modificata

durante l'esecuzione del sottoprogramma.Nel seguito useremo talvolta i termini parametri attuali e parametri muti in

luogo di argomenti attuali e argomenti muti rispettivamente.

14.3. Il corpo di un sottoprogramma e l'istruzione RETURN

Il corpo di un sottoprogramma è costituito da tutte le istruzioni che seguono

la prima. Esso deve c:ontenere tutte.le.frasi ir/(!iWJ~n§!lbili per una corretta ed auto­noma compi/azione del sottoprogramma. In particolare, qualorasian()uTilizz-ati

no~i- di v~riabiledimensionata~-d;~;o essere presenti nel corpo del sottopro­

gramma le opportune frasi di specificazione che possono riguardare anche nomi

presenti nella lista degli argomenti muti. Analogamente, possono seguire la prima

frase tutte le istruzioni di specificazione di tipo. lLcorpo di un sottoprogramma

de~nlln.unque terminare con t'tstrustane.~p il cui ~i~nifica!~p!!PtQ quellB

di se~~alare la fine delle istruzioni che costituiscono una unità di programma.

--Si osservi che tutt~i '!~~L~Iy~iiabf1eutii1Zzati in un qualunq~~Qn9PfOgram­ma-so-noloc~li n~l senso che ~~ni_!l~~~p~~ essere ~sa~o in lJn~tà di programma

distinte con significati completamente diversi.• ~A__.__ __

Comé è stato evidenziato anche in fig. 14.4 il corpo del sottoprogramma deve

contenere almeno una istruzione che ne interrompe l'esecuzione e trasferisce il

controllo all'unità chiamante. Tale istruzione, nella sua forma più semplice, è

costituita dalla sola parola chiave

RETURN

Un'altra forma di questa istruzione, utilizzabile però soltanto nei sottoprogrammi

SUBROUTINE. sarà vista nel capitolo seguente.

Si osservi che in F77 la sequenza di istruzioni

RETURN

END

è equivalente alla sola frase

END

Pertanto in F77 un sottoprogramma può non contenere la frase RETURN che in­

vece era obbligatoria in F66. Come è già stato osservato il ruolo della frase

RETURN in un sottoprogramma è analogo a quello della istruzione STOP nel

programma principale. A tale proposito si osservi che, mentre la frase RETURN

245

non deve far parte di un programma principale, l'istruzione STOP può essereutilizzata anche in un sottoprogramma ed il suo effetto è quello di interromperel'esecuzione del sottoprogramma senza provocare il rientro nell'unità di program­ma chiamante. In altri termini, l'esecuzione di una frase STOP all'interno di un

sottoprogramma causa la fine dell'esecuzione dell'intero programma.

14.4. I sottoprogrammi SUBROUTlNE e la frase CALL

I sottoprogrammi SUBROUTINE permettono di realizzare qualunque algo­

ritmo il cui risultato può essere costituito da più di un valore.

La prima istruzione

La prima frase di un sottoprogramma SUBROUTlNE ha la forma seguente:

SUBROUTINE nome (m" 01 2, .. " mn )

dove:• SUBROUTINE è la parola chiave che identifica la frase;• nome è un nome simbolico e costituisce il nome di sottoprogramma; esso

non deve comparzre_!!! ~~~~_istru~~~~~_erc?~p~clel sotto,,-rc!R~rnm,!; ----• mI' m2, ..., m

nsono gli argomenti muti del sottoprogramma. Ogni argomento

muto può essere un nome di variabile, un nome di variabile dimensionata un no­me di sottoprogra~ma, un asterisco. Gli argomenti muti costituiti da no'm~­bolici devono essere tutti distinti.

Un sottoprogramma SUBROUTINE può non avere argomenti muti; in questo

caso la prima istruzione può assumere una delle forme seguenti:

SUBROUTlNE nome tSUBROUTlNE nome

Esempio 14.2. Sono sin tatticamente corrette le istruzioni:

SUBROUTINE SIST (A, N, X, Y)SUBROUTINE COPIA(A, B)SUBROUTINE UN (XPl, XM2,SIGMA,*, -. *)SUBROUTINE STAMPA

Sono invece sbagliate le seguenti:

SUBROUTINE TRASP(A(l), N, X)SUBROUTINE LISTA(X, Y, 5)SUBROUTINE TEST (A, B, A + B)SUBROUTINE ESPER (X(4:), PAR)

Queste frasi infatti contengono, rispettivamente, un nome di elemento di varia­

bile dimensionata, una costante, una espressione, un nome di sottostringa.

Page 127: Fortran

!,I!

, I

246

Esempio 14.3. Il sottoprogramrna MAXMIN di fig. 14.5 permette di calcolare

il massimo ed il minimo fra tre numeri reali a, b, c. Gli argomenti muti del sotto­

programma sono A, B, C, MAX, MIN: i primi tre sono i nomi usati nel sottopro­

gramma per indicare le tre quantità a, b e c rispettivamente, mentre MAX e MIN

sono i nomi usati per indicare il massimo ed il minimo.

Confrontando il sottoprogramma di fig. 14.5 con il programma principale del­

l'esempio 9.12 si può notare che la frase STOP è stata sostituita dalla RETURN

e che le frasi di ingresso/uscita sono state eliminate in quanto le informazioni

relative ai dati e ai risultati vengono trasmesse tramite la lista degli argornenn

muti.

SUBROUTINE MAXMIN (A, B, C, MAX,MIN)REAL A, B, C, MAX,MINIF (A.GT.B) THEN

MAX=AELSE

MAX=BENDIFIF (C.GT.MAX) THEN

MAX=CENDIFIF (A.GT.B) THEN

MIN=BELSE

MIN=AENDIFIF (C.LT.MIN) THEN

MIN=CENDIFRETURNEND

Figura 14.5. Sottoprogramma per il calcolo del massimo e del minimo fra tre valori reali.

Esempio 14.4. Si vuole scrivere un sottoprogramrna che permetta di calcolare la

radice quadrata di un numero positivo x usando l'algoritmo di fig. 10.6.

L'esempio 10.14 fornisce un programma principale che risolve questo stesso

problema e che prevede operazioni di scrittura diverse per evidenziare il risultato.

Il sottoprogramma che viene ora richiesto può essere realizzato in modo da tra-

247

smettere in uscita tutte le informazioni relative al risultato ottenuto affinché l'uni­

tà di programma chiamante possa utilizzare tali informazioni per eseguire qualun­

que tipo di operazione sul risultato, comprese quelle di scrittura previste nell'e­

sempio 10.14. Per informare l'unità chiamante sul tipo di risultato ottenuto si

può prevedere, tra le informazioni in uscita, il valore di una variabile IND che nel

corpo del sottoprogramma viene posta uguale a zero se è verificata la condizione

1m2 - x I.,;;; G, uguale ad l in caso contrario. Il sottoprogramma richiesto è stato

chiamato RADQ, è di tipo SUBROUTINE ed utilizza nove argomenti muti il

cui significato è specificato mediante opportune frasi di commento.

ISUBROUTINE RADQ(X, SIGMA,NIT, SX, DX,IND, RAD, ERR, IT)

C SOTTOPROGRAMMA PER IL CALCOLODELLA RADICEQUADRATA DI X > OC ARGOMENTI MUTIDI INGRESSO:C X : NUMERO POSITIVODI CUI SI VUOL CALCOLARE LA RADICEC SIGMA: TOLLERANZAPER IL CRITERIO DI ARRESTOC NIT: NUMEROMASSIMO DI ITERAZIONIC ARGOMENTI MUTI DlINGRESSO/USCITA:C SX IN INGRESSO: NUMERO REALE MINOREDI XC DX IN INGRESSO: NUMERO REALE MAGGIORE DI XC AD OGNI ITERAZIONE IL VALORE DI SX O DI DX VIENE MODIFICATOC ARGOMENTI MUTI DI USCITA:C IND: VARIABILE DI CONTROLLO CON I SEGUENTIVALORIC = OSE IL CRITERIO DI ARRESTO E' SODDlSFATTOC = I ALTRIMENTIC RAD: PER IND = OE' L'APPROSSIMAZIONE DELLA RADICE DI XC ERR : PER IND = OE' L'ERRORE ABS(RAD .. 2 - X)C IT : PER IND = OE' IL NUMERO DI ITERAZIONI ESEGUITEC PER IND = l I VALORI DI RAD, ERR, IT SONO QUELLI RELATIVIC ALL'ULTIMA ITERAZIONEESEGUITA.

DO 150 IT = l, NITRAD = SX + 0.5 • (DX - SX)ERR = ABS(RAD .. 2 - X)IF (ERR.LE.SIGMA) THEN

IND=ORETURN

ELSE IF (RAD .. 2.GT.x) THENDX=RAD

ELSESX = RAD

END IF150 CONTINUE

IND = lEND

Esempio 14.5. L'algoritmo di fig. 14.6 risolve l'equazione ax 2 + bx + c = O, con

a *" O. Nell'algoritmo si considera nullo qualunque valore del discriminante

Page 128: Fortran

Riferimento ad un sottoprogramma SUBROUTlNE

Un sottoprogramma SUBROUTINE viene chiamato mediante una frase esegui­

bile la cui forma è la seguente:

dove:

• CALL è la parola chiave che identifica la frase;

• nome è il nome del sottoprogramma che si vuole attivare;

• al' a2, ..., an sono gli argomenti attuali ciascuno dei quali può essere costitui­

to da un nome di variabile, un nome di variabile dimensionata, un'espressione, un

nome di un altro sottoprogramma, uno specificatore di ritorno alternativo (cfr.

cap. 15). Il numero !kg!i argomenti attuali deve coincidere con quello degli argo­menti muti del ~~.!!Q.Q!og~~m-ma-chiamato. _- -- - - __o - ..-- - ---- ------ .-.-.

Se-if-sottoprogramma chiamato non ha argomenti muti la frase CALL può

avere una delle forme seguenti:

CALL nome ( )

CALL nomeL'effetto dell'esecuzione di una frase CALL è quello di attivare il sottopro­

gramma il cui nome è specificato nella frase e di riprendere il controllo dell'ese­cuzione al momento dell'uscita dal sottoprogramma.

248

1. Dati: a"* O, b, c, e > O2. Poni 6 = b2

- 4 ac3. SeI61";f,allora: poni ind e 1;

poni XI = - b/2a;poni X2 = XI;

esegui 4.altrimenti: se 6> e, allora: poni ind = 2;

se b < O,allora: poni s = - 1altrimenti: poni s =+ 1

poni XI =- (b + s -Ji.)/2a;poni X2 = c/(a xj );esegui 4.

altrimenti: poni ind = O;poni XI =- b/(2a);poni X2 =....et;/(2a),esegui 4.

4. Risultati: ind, XI, X2

5. Stop.

Figura 14.6. Algoritmo per la risoluzione di 02 + bx + c = O con a"* O.

t:. = b2 - 4 ac tale che It:.IE;;; f, con f> Oassegnato dipendente dalla precisione

di macchina; inoltre, t:. è considerato positivo se t:. > e e negativo se t:. < - f. Al

termine dell'algoritmo i risultati sono i seguenti:

ind = O se l'equazione non ha radici reali ovvero se t:. < O;

ind = l se l'equazione ha radici reali coincidenti ovvero se t:. = O;

ind = 2 se l'equazione ha radici reali distinte ovvero se Is> O;

Xl e x2 sono le radici dell'equazione se ind = l oppure ind = 2, mentre se

ind = O esse sono rispettivamente la parte reale e quella immaginaria delle due

radici complesse coniugate Xl ± i x2·

Si osservi che le eventuali radici reali e distinte dell'equazione vengono calcolate

secondo le formule

Xl = - (b + sign (b) Vi.)/2:+

x2 = c/(a Xl)

per limitare la propagazione degli errori di arrotondamento [lO].

Basandosi sull'algoritmo di fig. 14.6 si può scrivere il seguente sottoprogramma,

SOLV2, i cui argomenti muti A, B, C, EPS, X l, X2, IND rappresentano rispet­

tivamente a, b, c, e, xl' x2 ' ind.

l

cC

SUBROUTINE SOLV2 (A, B, C, EPS! Xl, X2, IND)RISOLUZIONE DI UN'EQUAZIONE DI SECONDO GRADOA • X u 2 + B • X + C = O, CON A DIVERSO DA ZERODELTA=Bu2-4.• A.CIF (ABS(DELTA).LE.EPS) THEN

IND = 1XI =-0.5. B/AX2 =Xl

ELSE IF (DELTA.GT.EPS) THENIND = 2 \IF (B.LT.O.) THEN

S=-1.ELSE

S=+1.ENDIFXI = - 0.5. (B + S. SQRT(DELTA»/AX2 = C/(A. XI)

ELSEIND = OXI =-0.5. B/AX2 = + 0.5. SQRT (- DELTA)/A

END IFRETURNEND

249

Page 129: Fortran

250 251

SUBROUTINE PROVA (X, N, Y)

SUBROUTINE RADQ (X, SIGMA, NIT, SX, DX, IND, RAD, ERR, IT)

Esempio 14~ 6. Dato il sottoprogramma definito dalla frase

Il programma richiesto può essere il seguente:

PROGRAM VALOR]C CALCOLO DE] VALORI l/SQRT(N), N = 2, ... ,50C SI UT]L1ZZA ]L SOTTOPROGRAMMA RADQC NEL PROGRAMMA PRINCIPALE GLI ARGOMENTI ATTUALIC HANNO GLI STESS] NOMI DE] CORR]SPONDENT] ARGOMENTIC MUT] AD ECCEZ]ONE DI X AL QUALE CORRISPONDE RN

READ ., S]GMA, NITPRINT 1000, S]GMA, NlTDO 100 N = 2, SORN=NSX= l.DX = N/2. + l. ICALL RADQ (RN, S]GM.\, NlT, SX, DX, IND, RAD, ERR,lT)IF (IND.EQ.l) THEN

PRINT 1500, NELSE

VAL= l./RADPRINT ]600, N, VAL, ERR, lT

END ]F100 CONTINUE

STOP1000 FORMAT (lX, 'TOLLERANZA:', EI3.6/

l IX, 'NUMERO MASSIMO DI lTERAZIONI:', BI)1500 FORMAT (lX,'PER N =',12/

l IX, 'NON E" SODDISFATTO IL CRITER]O DI ARRESTO')1600 FORMAT (lX,'PER N =', ]2/

1 ]X, 'VALORE CALCOLATO:', E13.6/2 IX, 'ERRORE COMMESSO:', E13.6/3 IX, 'NUMERO DI ITERAZ]ONI ESEGUITE:', 13).

END

Si osservi che il sottoprogramma RADQ utilizza un argomento di tipo reale, X,

per indicare la quantità di cui si vuoi determinare la radice quadrata. Ad X deve

quindi corrispondere un argomento attuale di tipo reale; da qui la necessità diassegnare, prima di ogni attivazione del sottoprogramma, alla variabile reale RN

il valore di N. Gli altri argomenti muti utilizzati dal sottoprogramrna corrispondo­

no, nel programma chiamante, ad argomenti attuali che hanno il loro stesso nome

e, mentre i valori di SIGMA e di NIT vengono definiti una sola volta nel program­

ma chiamante mediante una frase di lettura, quelli di SX e di DX devono essere

definiti prima di ogni chiamata del sottoprogramma in quanto essi vengono mo­

dificati durante l'esecuzione di RADQ. Dopo l'esecuzione del sottoprogramma

i risultati sono disponibili come valori degli argomenti attuali IND, RAD, ERR e

IT; in particolare il valore di IND viene usato dopo l'esecuzione della frase CALL

per effettuare operazioni di stampa diverse ciascuna delle quali metta in evidenza

le caratteristiche dei risultati ottenuti.

perché la lista degli argomenti attuali è composta dadue soli elementi;

perché, se Y è di tipo reale, il secondo argomento at­

tuale non è dello stesso tipo del corrispondente argo­mento muto.

CALL PROVA (X, N)

CALL PROVA (X, Y, Z)

CALL PROVA (A, M, Y)CALL PROVA (X + Y, L, Z)CALL PROVA (X, 15, Y)CALL PROVA (X, N + l, Y)CALL PROVA (A(3), N, 8(7»CALL PROVA (R(J), L, S(N + 2»

Esempio 14.7. Si vuoI scrivere un programma per calcolare e stampare i valori

l/~ per n = 2, 3, ..., 50.

Il problema può essere risolto usando il sottoprogramma descritto nell'esem­pio 14.4 definito dalla frase iniziale:

dove X ed Y sono nomi di variabili reali ed N quello di una variabile intera, sono

formalmente corrette le seguenti chiamate:

Con riferimento allo stesso sottoprogramma sono invece sbagliate le seguenti

frasi CALL:

L'attivazione del sottoprogramma avviene associando, nell'ordine, gli argo­

menti attuali al' a2, ... , an a quelli muti mI' m2, ... , mn ~ Per una cor~~tta asso­ciazione tra gli argomenti attuali e quelli muti occorre che ogni a. sia dello stessoI _. __ -

tipo delcorrispondente mi; inoltre, se mi è il nome di un sottoprogramma anche

ai deve esserlo mentre s-e mi è un asterisco, allora ai deve essere uno specificatoredi ritorno alternativo. In altri termini, le due liste di argomenti devono accordarsiin ordine. numero e tipo.

r Al momento dell'esecuzione di una frase CALL gli argomenti attuali corrispon-

l)denti agli argomenti muti di ingresso devono contenere le informazioni necessarie : I

I·. all'esecuzione del sottoprogramma. Dopo l'esecuzione del sottoprograrnrna, ì l! \1Il~ risultati ottenuti sono disponibili per l'unità chiamante come valori degli argo- ili, j

menti attuali corrispondenti agli argomenti muti di uscita. IiI

,I

Page 130: Fortran

I252 253

tipo FUNCTION nome ( )

Esempio 14.9. Sono formalmente corrette le seguenti frasi iniziali:

REAL FUNCTION MEDIA (V, N)INTEGER FUNCTION FUNZ (X, Y)FUNCTION FATT (N)FUNCTION EPSM ( )CHARACTER * 8 FUNCTION LISTA (CAR)

FUNCTIONtipodove:

• tipo è uno specificatore di tipo che può essere omesso; se presente, esso devecoincidere con uno degli specificatori INTEGER, REAL, DOUBLE PRECISION,

COMPLEX, LOGICAL oppure CHARACTER *Q;

• FUNCTION è la parola chiave che identifica la frase;• nome è un nome simbolico che costituisce il nome del sottoprogramma;

• m}' m2, .. "' mn sono gli argomenti muti che devono essere tutti distinti; ogniargomento muto può essere un nome di variabile, di variabile dimensionata o disottoprogramma.

Se il sottoprogramma FUNCTION non prevede argomenti muti, la sua primafrase deve avere la forma:

PROGRAM MAINREAL MAX,MINREAD '(3FlO.2)', X, Y, ZCALL MAXMIN (X, Y, Z, MAX,MIN)IF (MAX.NE.O.) THEN

READ '(F 10.2)', EPSCALL SOLV2(MAX, MIN, 1., EPS, Xl, X2,IND)PRiNT 1000, MAX, MIN, 1., IND

ELSEPRiNT 2000

END IFSTOP

1000 FORMAT (IX, 'COEFFICIENTI DELLA EQUAZIONE:',3(2X, E13.6)/1 IX, 'NUMERODI RADICI REALI:', 12)

2000 FORMAT (IX, 'L"EQUAZIONE E" DI PRIMOGRAOO')END

Esempio 14.8. Si vuoi scrivere un programma che permetta di stabilire il numero

di radici reali distinte dell'equazione di secondo grado ax2 + bx + l = O dove ae b sono rispettivamente il massimo ed il minimo di tre valori dati x, y e z.

Il programma richiesto può utilizzare i sottoprograrnrru MAXMIN e SOL V2

già descritti rispettivamente negli esempi 14.3 e 14.5 e può essere realizzato nel

modo seguente:

Nel programma MAIN l'esecuzione della frase

CALL MAXMIN (X, Y, Z, MAX, MIN)

permette di calcolare il massimo, MAX, ed il minimo, MIN, dei tre valori dati.

L'esecuzione del programma prosegue poi con il controllo sul valore di MAX: se

MAX è uguale a zero si esegue l'operazione di scrittura che provoca la riprodu­

zione del messaggio: L'EQUAZIONE E' DI PRIMO GRADO e il programma

termina; altrimenti si legge il valore della variabile EPS e si attiva il sottoprogram­

ma SOLV2 per risolvere l'equazione di secondo grado ax2 + bx + c = O con a == MAX, b = MIN, c = 1.

14.5. I sottoprogrammi FUNCTION

I sottoprogrammi di tipo FUNCfION hanno lo scopo di reé!li~~re.-JÙgOritmi

chefomiscono come risultato un !-J!1J~ valore. Per questo motivo tali sottopro­grammi sono detti anche funzioni esterne eà il loro risultato è detto valore dellafunzione.

La prima istruzione

La prima frase di un sottoprogramma di tipo FUNCfION è una istruzione non

eseguibile che ha la forma

Il valore di un sottoprogramma FUNCTION ed il suo tipo

Diversamente da quanto detto per il nome di un sottoprogramma SUBROUTlNE

il nome di una funzioneestema deve comparire come nome di variabile nelcorpo della f~;'~i~--;;e stessa almeno in una frase eseguibile che ne definisca il valo­

re, Il nome di unl! f!!!1~ione esterna iQ~!Hifk.ainfaJtj li! 19ç~jQ~~ !iella quale vienememorizzato il risultato del sottoprogramma, ovvero il valore della funzione:II--tipo-dellavarlabile U-cù-i-nome~oin~id-~--;;;nil nome della funzione ovvero il

tipo del suo valore, è detto tipo della funzione, e può essere dichiarato esplicita­

mente nella prima frase mediante lo specificatore di tipo in essa contenuto.La specificazione del tipo di una funzione esterna può avvenire arlC11è-òèfcorpo

del sottoprogramma mediante un'opportuna frase dichiarativa. Così, ad esempio,l'istruzione

REAL FUNCTION MEDIA (V, N)

specifica che il sottoprogramma FUNCTION fornisce un risultato reale in quanto

il nome MEDIA è di tipo reale; lo stesso effetto sarebbe stato ottenuto con lasequenza di istruzioni

FUNCTION MEDIA (V, N)REAL MEDIA

l

Page 131: Fortran

254255

L'unico risultato del sottoprogramma è EPSM e la lista degli argomenti è vuotaperché non ci sono dati in ingresso.

Esempio 14.12. Scrivere un sottoprogramma che, data la coppia di valori (x. v),

calcoli il valore z = ftx, y) con

altrimenti

per x~ O e y ~ O

Il seguente sottoprogramrna, di nome ZETA, risolve il problema dato; i due

argomenti muti rappresentano la coppia di dati x ed y e ZETA contiene, al ter­mine dell'esecuzione del sottoprogramrna, il valore ft x, y).

REAL FUNCTION ZETA (X, Y)REAL X,YIF (X.LT.O..OR.Y.LT.O.) THEN

ZETA = SQRT (EXP(X» + SQRT (EXP(Y»ELSE

ZETA = SQRT(X) + SQRT(Y)END IFRETURNEND

REAL FUNCTION EPSM ( )C CALCOLO DELLA PRECISIONE DI MACCHINA

EPSM = 1.lO EPSM =0.5 • EPSM

A = 1. + EPSMIF (A.GT.1.) GO TO lOEPSM = 2.• EPSMRETURNEND

f(x, y) =

Esempio 14.13. La seguente funzione esterna calcola una stima della precisione

di macchina €m disponibile su un elaboratore quando si lavora in precisione sem­

plice. L'algoritmo si basa sulla considerazione che la precisione di macchina può

essere stimata come il più piccolo numero positivo che, sommato ad l, viene«sentito» dall'elaboratore (cfr. [9], [IO]).

Si osservi che il nome FATI del sottoprogramma compare più volte nel corpo

della funzione; la prima volta il suo valore è posto uguale ad l; successivamente,

se n > l, il contenuto di FATI viene modificato all'interno del ciclo-DO in modoche, alla fine del ciclo, FATI contiene il valore n!

Esempio 14.11. Si vuoI scrivere un sottoprogramma che calcola il fattoriale n!

di un numero intero n ~ O. Ricordiamo che n! è definito da:

I sen=O

n'=/. "il i se n > O

i= l

Esempio 14.10. La sequenza di istruzioni

(l' jREAL FUNCTION VAL (A, B) iiI ll~MPLICIT DOUBLE PRECISION (R - Z) v V\.

definisce una funzione di nome VAL e di tipo reale; tutti i nomi simbolici presenti

nel corpo del sottoprogramma le cui lettere iniziali siano comprese, nell'ordina­

mento alfabetico, tra R e Z sono di tipo doppia precisione ad eccezione del nomeVAL. Lo stesso effetto è ottenuto con la sequenza:

FUNCTION VAL (A, B)IMPLICIT DOUBLE PRECISION (R - Z)REAL VAL

In F66 il tipo di una funzione esterna non poteva essere specificato nel corpodel sottoprogramrna, ma solo nella prima frase.

Si osservi che il valore da calcolare cresce rapidamente al crescere di n; pertanto

è opportuno valutare n! usando l'aritmetica reale in modo da limitare la possi­

bilità di overflow. Il sottoprogramma richiesto può essere quindi una funzione

esterna identificata da un nome di tipo reale quale, ad esempio, la seguente:

REAL FUNCTION FATT (N)C CALCOLA N! CON N NON NEGATIVO

FATI = 1.IF (N.GT.l) THEN

DO lO 1= 2, NlO FATI =FATI. I

ELSEEND IFRETURNEND

Si osservi che la sequenza di istruzioni

REAL FUNCTION MEDIA (V, N)REAL MEDIA

ryv è sbagliata in quanto, in una stessa unità di programma, il tipo di una variabile /0 'non può essere specificato in più istruzioni. )

Il tipo di un sottoprogramma FUNCfION può essere definito anche in modo

implicito dalla lettera iniziale del suo nome. Va notato comunque che una dichia­

razione esplicita di tipo presente nella prima frase del sottoprogramma annullal'effetto di eventuali istruzioni IMPLICIT.

J,\~ ,

';1

II~,l

Page 132: Fortran

256 257

Riferimento ad un sottoprogramma FUNCTlON

Un sottoprogramma FUNCTION può essere chiamato da un'altra unità diprogramma utilizzando, in una qualunque espressione, un riferimento della forma

L'esecuzione di un riferimento ad una funzione esterna consiste nella attiva­

zione, esecuzione e uscita dal sottoprogramma il cui nome è specificato nel ri­ferimento. L'esecuzione del programma chiamante prosegue quindi con l'utiliz­

zazione del risultato fornito dal sottoprogramma.

sen~k~O

n!

REAL A(IO, lO), COEFF

I :

altrimenti- I

r(n, k) = k! (n - k)!

Esempio 14.15. Dati due numeri interi n e k scrivere un sottoprogramma che per­

metta di calcolare il valore r (n, k) definito da:

Il sottoprogramma richiesto può essere il seguente:

FUNCTION COEFF (N, K)REAL COEFF, FATTINTEGER N, KIF (N.GE.K.AND.K.GE.O) THEN

COEFF = FATT(N)/(FATT(K). FATT(N - K»ELSE

COEFF = - l.ENDIFRETURNEND

Si osservi che questo sottoprogramma richiama il sottoprogramma FATT (cfr.

esempio 14.11) per calcolare n!, k! e (n - k)!. Il sottoprogramma FATI è utiliz­

zato tre volte nella stessa espressione mediante il suo nome seguito dall'indica­

zione dell'argomento attuale. Ogni riferimento alla funzione esterna FATI pro­

voca l'attivazione del sottoprogramma, la sua esecuzione e quindi la disponibilità

del suo risultato.

Se gli elementi aj,j di una matrice A quadrata di ordine n = lO sono definiti da

ai,j = r (i, j) i = l, ... , n, j = l, ... , n

essi possono essere calcolati usando le seguenti istruzioni:

REAL FUNCTION FUNZ (X, N)

nome ( )

Esempio 14.14. Sono formalmente corretti i riferimenti al sottoprogramma de­

finito dalla frase

contenuti nelle istruzioni seguenti:

B = FUNl (X, N)R = ABS (FUNl (l, 5) + FUNl (X + Y, L»PRINT '(IX, "VALORE DELLA FUNlIONE", E13.6)', FUNZ (V, N)IF (FUNl (A, L).GT.FUNl (A + 0.5 • H, lO» THENIF (X.GT.V) V = FUNl (X - Y, I)

dove:

• nome è il nome del sottoprogramma FUNCTION;

• al' a2, •.• , an sono gli argomenti attuali ciascuno dei quali può essere unnome di variabile, un nome di variabile dimensionata, un'espressione, o il nome

di un altro sottoprogramma. La lista degli argomenti attuali deve accordarsi innumero, ordine e tipo di elementi con quella degli argomenti muti della funzione

esterna chiamata.

Si noti che un riferimento ad una funzione esterna può comparire anche nella

lista di una frase PRINT o WRITE, purché l'esecuzione del sottoprogramma nonrichieda a sua volta operazioni di uscita.

Un riferimento ad una funzione esterna che non prevede argomenti muti hala forma:

I Il tipo del nome di una funzione esterna deve risultare, in ogni unità chiamante, ~

, uguale al tipo della funzione; così, ad esempio, il sottoprogramma definito dalla 111'v

frase

DOUBLE PRECISION FUNCTION VAL (X, Y)

deve essere usato in unità di programma che contengano la frase

DO 20 J = l, ioDO 20 1= 1, lOA(I, J) =' COEFF (I, J)

20 CONTINUEDOUBLE PRECISION VAL

oppure in unità di programma in cui sono implicitamente definite di tipo doppia

precisione tutte le variabili il cui nome inizia con la lettera V.In questa sequenza di istruzioni A(l, 1) è interpretato come un nome di ele­

mento di matrice mentre COEFF(l, 1) è interpretato come riferimento ad una

Page 133: Fortran

li

I

258

funzione esterna. Queste diverse interpretazioni derivano dalla presenza della

frase

REAL A( l O, ioi, COEFF

che definisce soltanto A come nome di matrice.

Sottoprogrammi FUNCTION di tipo carattere

Una funzione esterna è di tipo carattere se il suo nome è dichiarato, nella prima

frase o nel corpo del sottoprogramma, di tipo carattere. La lunghezza Qspecifica­

ta per il nome di una funzione esterna è detta lunghezza della funzione e indica

la lunghezza del suo valore. La lunghezza di una funzione di tipo carattere può

essere espressa in uno dei modi previsti nel cap. 12 per le variabili di questo tipo

eccetto che tramite un'espressione costante intera in cui compaiono nomi simbo­

lici di costante. Se la specuicazione della lunghezza non è presente, allora la fun­

zione ha lunghezza l.

Esempio 14.16. Le frasi seguenti

CHARACTER • lO FUNCTJON STR (X)CHARACTER FUNCTION VOCE (Y)

sono corrette e definiscono due funzioni di tipo carattere che hanno, rispettiva­mente, lunghezza 10 e l. La seguente definizione della funzione carattere

CHARACTER. (LUN) FUNCTJON ERRATO (X)PARAMETER (LUN = lO)

è invece sbagliata perché la lunghezza della funzione è specificata tramite un nome

simbolico di costante. Per lo stesso motivo è sbagliata la definizione seguente:

FUNCTJON ERRATO (X)PARAMETER (LUN = JO)CHARACTER • (LUN) ERRATO

In ogni unità di programma in cui si usa una funzione esterna di tipo carattere,

il nome della funzione deve essere di tipo carattere e la sua lunghezza deve essere

uguale a quella della funzione e deve essere espressa in uno dei modi previsti nel

cap. 12 eccetto che tramite uno specificatore di lunghezza indefinita. Così, con

riferimento alle funzioni definite nell'esempio 14.16, le unità di programma chia­

manti devono contenere le dichiarazioni

CHARACTER • lO STRCHARACTER VOCE

259

Osserviamo che la lunghezza di una funzione carattere può essere espressa median­

te uno specificatore di lunghezza indefinita (*); in questo caso la lunghezza effet­

tiva del risultato viene stabilita al momento della chiamata e viene posta uguale al­

la lunghezza che il nome della funzione ha nell'unità di programma chiamante.

Esempio 14.17. Supponiamo che la funzione

CHARACTER • (.) FUNCTJON NOME (C)

sia utilizzata da due unità di programma Pl e P2 contenenti, rispettivamente,le dichiarazioni:

CHARACTER.25 NOMECHARACTER • lO NOME

Allora la funzione NOME fornisce un risultato di lunghezza 25 ogni volta cheviene utilizzata da P I mentre fornisce un risultato di lunghezza lO quando vieneutilizzata da P2.

14.6. Le funzioni definite da una frase

In ogni unità di programma si possono definire ed usare delle funzioni defini­te da una frase ovvero funzioni che, come dice il loro nome, sono definite da unaunica istruzione non eseguibile della forma:

dove:

• nome è il nome simbolico della funzione; il tipo di nome è il tipo della fun­zione;

• m)' m2, ... , mn sono gli argomenti muti che devono essere nomi distinti divariabile;

• e è un'espressione FORTRAN che può contenere, oltre agli argomenti muti

anche costanti, nomi simbolici di costante, nomi di variabile o di elementi di varia­

bile dimensionata che compaiono nella stessa unità di programma. Questa espres­

sione può anche contenere riferimenti a funzioni intrinseche o a funzioni esternee riferimenti ad altre funzioni definite da un'istruzione.

La frase che definisce una funzione deve precedere tutte le frasi eseguibili e se­

guire tutte le frasi dichiarative presenti nell'unità di programma in cui essa com­

pare. Inoltre una funzione definita da una frase deve essere preceduta da tutte le

altre funzioni definite da una frase da essa eventualmente utilizzate.

L'espressione che compare nella frase di definizione di una funzione di tipo

numerico (intero, reale, doppia precisione o complesso) può avere tipo diverso

Page 134: Fortran

260

dalla funzione, ma non può essere un'espressione logica o carattere; inoltre essanon può essere di tipo complesso se la funzione è di tipo doppia precisione eviceversa.

Esempio J4. J8. Sono sin tatticamente corrette le seguenti frasi di definizione difunzioni:

TRASL(X) = (- 2./(A - B». X + (A + B)/(A - B)F(X, Y) = SQRT(X •• 2 + y •• 2)

La frase:

STATUS(A, B, C) =ABS(A - B).LT.EPS.OR.C.GT.O.

è corretta solo se è preceduta dalla specificazione

LOGICAL STATUS

Una funzione definita da un 'istruzione può essere usat~ soll1ll1.liL4a/l'unit~

dip!ç}g[!!!!U!1fl in cui essa è.detìnit.a..L'utilizzazione di una funzione definita dauna frase avviene mediante un riferimento della forma:

/ nome (al' a2 , .... , an

),dove:

• nome è il nome della funzione;

• al' a2, •.•, an sono gli argomenti attuali ciascuno dei quali può essere unaespressione; la lista degli argomenti attuali deve accordarsi in numero, ordine etipo con quella degli argomenti muti.

L'esecuzione del riferimento avviene nel modo seguente: gli argomenti attualivengono associati a quelli muti e viene quindi calcolato il valore dell'espressione

che compare nella frase di definizione della funzione usando, in corrispondenza

degli argomenti muti, i valori degli argomenti attuali. Il valore dell'espressione,

eventualmente convertito al tipo della funzione secondo le regole dell'assegnazio­ne, costituisce il risultato della funzione.

Esempio J4. J9. Consideriamo il seguente programma:

PROGRAM TABF(X) = X .. 3 - SIN (X •• 2)READ -. XO, H, NDO lO l =0, NX = XO + l. HPRINT '(IX, /IX =/1, EI3.6, IX, /lF(X) =/1, EI3.6)', X, F(X)

lO CONTINUESTOPEND

261

Lo scopo del programma è quello di scrivere i valori della funzione

f(x) = x3 - sen(x2 )

nei punti Xi = Xo + ih, con i = O, ... , n supponendo noti xo' h, n.

Nell'istruzione che definisce la funzione di nome F, l'unico argomento muto

è X. Si osservi che non c'è nessun conflitto né ambiguità sul ruolo del nome X

nel programma TAB anche se esso viene usato in altre istruzioni. Infatti al mo­

mento della definizione di F, X rappresenta l'argomento muto, mentre dentro al

ciclo-DO esso è il nome della variabile che contiene il valore di Xi' Al momento

dell'attivazione di F, ovvero nella frase di scrittura, X è l'argomento attuale.

Osserviamo che lo stesso risultato del programma TAB può essere ottenuto

con il programma seguente, costituito dal programma principale TAB2 e dalla

funzione esterna F

PROGRAM TAB2READ -. XO, H, NDO lO I =0, NXT = XO + I. HPRINT '(IX, "X = ".E13.6, IX, "F(X) = ",EI3.6)', XT, F(XT)

io CONTINUESTOPEND

FUNCTION F(X)F = X •• 3 - SIN (X •• 2)RETURNEND

14.7. Le funzioni intrinseche

Come è stato sottolineato anche all'inizio di questo capitolo, le funzioni in­

trinseche non sono altro che particolari sottoprogrammi che ogni sistema mette

a disposizione dell'utente. Nel cap. 6 si sono descritte alcune funzioni di uso

estremamente comune nelle applicazioni, ma in F77 sono previste molte altre

funzioni il cui significato è descritto in questo paragrafo. Ricordiamo che per

utilizzare correttamente qualunque funzione intrinseca si devono seguire le re­

gole seguenti:• il numero di argomenti attuali deve coincidere con il numero di argomenti

specificato per la funzione;

• il tipo degli argomenti attuali deve essere uno dei tipi previsti per gli argomenti

della funzione;• se gli argomenti attuali sono più di uno, essi devono essere tutti dello stesso

tipo.

Ricordiamo anche che quando una funzione intrinseca può essere usata con ar-

!\ ,! .

Page 135: Fortran

262

Le funzioni di conversione numenca

Le funzioni che consentono di passare da una rappresentazione interna di un

dato numerico ad un'altra sono dette funzioni di conversione numer!ca._l.r- loro

caratteristiche sono riassunte in fig. 14.7 insieme a quelle di alcune funzioni

intrinseche da esse derivate e di altre destinate al trattamento dei numeri com­

pIessi: per ognuna di queste funzioni si riportano in figura il numero di argomenti,

il nome generico e/o i nomi specifici, il tipo di argomenti e il tipo del risultato.

I simboli I, R, Dp, C indicano rispettivamente il tipo intero, reale, doppia preci­

sione e complesso.

gomenti di tipo diverso, il tipo del risultato è determinato da quello degli argomenti

attuali, Così, ad esempio, la funzione intrinseca ABS può operare su un argomen­

to di tipo intero, reale, doppia precisione oppure complesso. Nei primi tre casi

la funzione ABS fornisce il valore assoluto della quantità specificata quale argo­

mento attuale ed il suo risultato è dello stesso tipo dell'argomento attuale; nel­

l'ultimo caso, ovvero se l'argomento attuale è di tipo complesso, la funzione ABS

dà come risultato un valore reale che è il modulo dell'argomento. Con un unico

nome, ABS, è pertanto possibile indicare operazioni diverse in base al tipo del­

l'argomento usato. La caratteristica di indicare con lo st~sso ~~~e di funzione(nome generico) operazioni diverse è comune a molte funzioni intriJ1sec~e:­

L'utilizzazione del nome generico permette quindi di selezionare, mediante il

tipo degli argomenti, le operazioni che devono essere eseguite per ottenere un

I risultato coerente con i dati forniti alla funzione. Questa flessibilità delle funZiO~i.i

fhI:! intrinseche rispetto al tipo dei loro argomenti, deriva dal fatto che ciascun nome! ~t1I ~\ generico indica una famiglia di funzioni ciascuna delle quali opera su un deter~

minato tipo di argomenti per fornire uno specifico risultato. Il tipo degli argmenti attuali che, in un riferimento alla funzione, accompagnano il nome generico

determina quale sottoprogramma della famiglia deve essere effettivamente utiliz­

zato e determina quindi il risultato della funzione. Nella maggior parte dei casi,

ogni sottoprogramma della famiglia identificata da ù----nnome -generico di funzione-pUò--~s~e~~-utilizzatoanche--mediatrt; un ~~o no~e spectfico,In ~ocaso gli­

argomenti attuali devono essere d~i -tipop~vistoper quèIp;rticolare sottopro­

gramma. Riprendendo l'esempio della funzione ABS essa indica una famiglia di

quattro sottoprogrammi le cui caratteristiche possono essere così riassunte:

263

Figura 14.7. Funzioni di conversione numerica.

Descrizione della funzione numero nome nome tipo tipo

argomenti generico specifico argomenti risultato

Conversione al tipo intero l lNT - I I

con troncamento INT,IFIX R I

(cfr.Oss.14.1) IDINT Dp I

- C I

Conversione al tipo reale l REAL REAL, FLOAT I R

(cfr. Oss. 14.2) - R R

SNGL Dp R- C R

Conversione al tipo doppia l DBLE - I Dp

precisione (cfr. Osso 14.3) - R Dp

- Dp Dp

- C Dp

Conversione al tipo 102 CMPLX - I C

complesso - R C

(cfr. Oss. 14.4) - Dp C- C C

Parte immaginaria di un l - AIMAG C R

numero complesso Dp

Complesso coniugato l - CONJG C CDp

Conversione al tipo intero l NINT NINT R I

con arrotondamento IDNINT Dp I

(cfr. Oss. 14.5)

Troncamento di un numero l AINT AINT R Rreale (cfr. Osso 14.6) DlNT Dp R

Arrotondamento di un l ANINT ANINT R Rnumero reale (cfr.Oss. 14.7) DNINT Dp Dp

1IIII

Tipo del risultato

Intero

Reale

Doppia precisione

Reale

Tipo dell'argomento

Intero

Reale

Doppia precisione

Complesso

Nome specifico

IABS

ABS

DABS

CABS

Page 136: Fortran

264 265

Osservazione 14.6. La funzione AINT è definita da:

te immaginaria uguale a REAL(~). Il valore di CMPLX (X, Y) è quindi il nu­

mero complesso con parte reale X e parte immaginaria Y, mentre il valore di

CMPLX (X + 3., 2.) è il numero complesso che ha parte reale uguale al valore

dell'espressione X + 3. e parte immaginaria uguale a 2.

Osservazione 14.5. La funzione NINT converte un dato reale o doppia preci­sione al tipo intero. Questa funzjone differisce da INT in gU~!!!Qla J:onvefSiGRe-.­

avviene per arrotondamento e Eon per troncamento: più precisamente si ha

NINT(a) = INT (a + 0.5) se a;;;:' ONINT(a) = INT (a - 0.5) se a < O.

Osservazioni sulle funzioni di conversione numerica

Osservazione 14.1. La funzione INT effettua la conversione al tipo intero di un

dato numerico, mediante troncamento.

Per a di tipo intero, INT(a) è uguale ad a.

Per a di tipo reale o doppia precisione, si distinguono due casi: se Ia I< l, al­lora lNT (a) = O; altrimenti il valore di INT (a) è un intero il cui segno coincide

con quello di a e il cui valore assoluto è il più grande intero che non supera Ia I.Così. ad esempio, INT (3.7) e INT (- 3.7) valgono rispettivamente 3 e - 3.

Per a di tipo complesso, il valore INT(a) è ottenuto applicando la regola prece­

dente alla parte reale di a.

Si osservi che non sono previsti nomi specifici per questa funzione quando gli

argomenti sono di tipo intero o complesso e che i nomi specifici IFIX e IDINT

sono stati mantenuti in F77 per compatibilità con il precedente standard. AINT(a) = REAL (lNT(a» se

AINT(a) = DBLE (lNT(a» se

a è di tipo reale

a è di tipo doppia precisione

Le funzioni matematiche

In fig. 14.8 sono riassunte le caratteristiche delle funzioni intrinseche previste

in F77 per la realizzazione di funzioni matematiche quali la radice quadrata, l'e­

sponenziale, il logaritmo, ecc. Le notazioni usate in fig. 14.8 sono le stesse già

usate in fig. 14.7.Per molte funzioni intrinseche di questa classe sono previste alcune restrizioni

sui valori degli argomenti in quanto il dominio delle corrispondenti funzioni ma­

tematiche è un sottoinsieme dell'insieme dei numeri reali o dei numeri com­

plessi. Tali restrizioni sono in generale diverse per argomenti reali e doppia preci­sione o per argomenti complessi; in ogni caso esse restano valide sia quando ci si

riferisce ad una funzione intrinseca con un nome specifico sia quando si usa il

nome generico.

Osservazione 14.2. La funzione REAL effettua la conversione al tipo reale di un

dato numerico.

Per a di tipo reale, REAL(a) è uguale ad a.

Per a di tipo intero o doppia precisione, REAL(a) fornisce la rappresentazione

interna del valore di a in floating-point in precisione semplice.

Per a di tipo complesso, REAL(a) è la parte reale di a.

Si osservi che non sono previsti nomi specifici per questa funzione quando gli ar­

gomenti sono di tipo reale e complesso, e che i nomi specifici FLOAT e SNGL

sono stati mantenuti in F77 per compatibilità con il precedente standard.

Osservazione 14.3. La funzione DBLE effettua la conversione al tipo doppia

precisione di un dato numerico.

Per a di tipo doppia precisione, DBLE(a) = a.Per a di tipo intero o reale, DBLE(a) fornisce la rappresentazione interna del

valore di a in doppia precisione.

Per a di tipo complesso, DBLE(a) è la rappresentazione in doppia precisione del­

la parte reale di a.

Osservazione 14.7. La funzione ANINT è definita da:

ANINT(a) = REAL (NINT(a» se

ANINT(a) = DBLE (NINT(a» se

a è di tipo realea è di tipo doppia precisione

Osservazione 14.4. La funzione CMPLX può avere uno o due argomenti. Se l'ar­

gomento è uno solo, questo può essere di tipo intero, reale, doppia precisione o

complesso, mentre se gli argomenti sono due essi non possono essere di tipo

complesso.

CMPLX(a) è uguale ad a se a è complesso; altrimenti CMPLX(a) è il numero

complesso con parte reale uguale a REAL(a) e parte immaginaria uguale a zero.

CMPLX (al' a2) è il numero complesso con parte reale uguale a REAL(al) e par-

Osservazioni alla figura 14.8

Osservazione 14.8. Il valore dell'argomento di SQRT e DSQRT deve essere mag­

giore o uguale di zero, mentre quello dell'argomento di CSQRT può essere un qua­

lunque numero complesso. Indicando con Q' + i (3 il valore dell'argomento e con

'Y + i<5 il risultato di CSQRT, si ha: 'Y = 6 = O se Q' = (3 = O; altrimenti 'Y + i<5 è

quella radice di Q' + i(3 per cui è 'Y;;;:' Oe, se 'Y = O, è 6 ;;;:. O.

Page 137: Fortran

266

Descrizione della funzione Numero di Nome Nomi I Tipo di Tipo delargomenti generico specifici argomenti risultato

Valore assoluto o modulo I ABS IABS I IABS R R

DABS Dp DpCABS C C

Radicc quadrata I SQRT SQRT R R(cfr. 055. 14.8) DSQRT Dp Dp

eSQRT C C

Esponenziale I EXP EXP R RDEXP Dp DpCEXP C C

Logaritmo naturale I LOG ALOG R R(cfr. Osso 14.9) DLOG Dp Dp

CLOG C C

Logaritmo in base dieci I LOGIO ALOGIO R R(cfr. 055. 14.9) DLOGIO Dp Dp

Seno (cfr. 055. 14.10) I SIN SIN R RDSIN Dp DpCSIN C C

Coseno (cfr. 055. 14.10) I eos eos R RDCOS Dp Dpecos C C

Tangente (cfr. Osso 14.10) I TAN TAN R RDTAN Dp Dp

Arcoseno (cfr. 055. 14.11) I ASIN ASIN R RDASIN Dp Dp

Arcocoseno I AeOS ACOS R R(cfr. Oss.14.11) DACOS Dp Dp

Arcotangente con un I ATAN ATAN R R

argomento (cfr. 055.14.12) DATAN Dp Dp

Arcotangente con due 2 ATAN2 ATAN2 R Rargomenti (cfr. Osso 14.13) DATAN2 Dp Dp

Seno iperbolico I SINH SINH R RDSINH Dp Dp

Coseno iperbolico 1 COSH eosli R RDeOSII Dp Dp

Tangente iperbolica 1 TANH TANH R RDTANH Dp Dp

Figura 14.8. Funzioni intrinseche matematiche.

267

Osservazione 14.9. Il valore dell'argomento di ALOG, DLOG, ALOGIO e DLOGIOdeve essere maggiore di zero, mentre quello dell'argomento di CLOG deve es­

sere diverso da zero. Indicando con a + il3 il valore dell'argomento e con "y + icS

il risultato di CLOG, si ha che "y + icS è il valore principale dellogarit~odi a + i/3,per il quale è - 1r < cS ~ 1re cS = 1rsoltanto se a < O e 13 = o.

Osservazione 14.10. Le funzioni SIN, COS, TAN e DSIN, DCOS, DTAN calcola­

no seno, coseno e tangente di un angolo espresso in radianti.

Osservazione 14.11. Il valore assoluto dell'argomento di ACOS, DACOS, ASIN

e DASIN deve essere minore o uguale di l.

Osservazione 14.12. Il valore di ATAN(a), per a di tipo reale o doppia precisione,

è l'arcotangente di a se Ia I~ a, dove a è una quantità positiva dipendente dalla

particolare realizzazione della funzione ATAN. Se a < - a, allora il valore di

ATAN(a) è - 1r/2, mentre se a> a il valore di ATAN(a) è 1r/2.

Osservazione 14.13. Legata al calcolo dell'arcotangente è anche la funzione

ATAN2 che prevede due argomenti, di tipo reale o doppia precisione, almeno uno

dei quali diverso da zero. Infatti il risultato r di ATAN2 (al' a2) è così definito:

_ se al> O e a2

=1= O, allora r è tale che tg(r) = al/a2 e 0< r < 1r

- se al = O e a2> O, allora r = O

- se al = O e a2 < O, allora r = 1r_ se al < O e a

2=1= O, allora r è tale che tg(r) = al/a 2 e - 1r< r < O

_ se a2

= O allora r può valere 1r/2 o - 1r/2 a seconda della particolare realiz-

zazione della funzione.

Le funzioni intrinseche per la manipolazione dei caratteri

Per la manipolazione dei caratteri sono previste in F77 le funzioni intrinseche

LGE, LGT, LLE, LLT, INDEX, ICHAR e CHAR il cui significato è stato spiegato

nel cap. 12 e la funzione intrinseca LEN che permette di calcolare la lunghezza di

un dato di tipo carattere il cui utilizzo verrà esemplificato nel cap. 15. Per como­

dità riportiamo nella fig. 14.9 le caratteristiche di queste funzioni; per ognuna di

esse la figura comprende una breve descrizione del significato, il numero di argo­

menti, il nome specifico (non esistono nomi generici per queste funzioni) e iltipo degli argomenti e del risultato (Cr sta per «carattere», L sta per «logico» e l

sta per «intero»).

Il

r1I

'1' l,l,Il!'

Page 138: Fortran

Figun 14.10. Altre funzioni intrinseche.

269

SIGN (l., a) = l. se a> O

SIGN (l., a) = - 1. se a < O

l'JI\

I

,I) "

. I·l

se a l * Oe a2 ;;. Ose al * O e a2 < Ose al = O

SIGN (al; a2) = Iali

SIGN (al' a2) =-I aliSIGN (al' a2) = O

Si osservi che le funzioni SIGN, ISIGN e DSIGN in F66 erano definite nel modo

sopra indicato per a2 * O, ma non erano definite per a2 = O.Dalla definizione segue che

Numero Nome Nomi Tipo di Tipo delDescrizione della funzione di argo- generico specifici argomenti risultato

menti

Resto della divisione intera 2 MOD MOD l l(cfr. Oss. 14.14) AMOD R R

DMOD Dp Dp

Trasferimento di segno 2 SIGN ISIGN I 1(cfr. Osso 14.15) SIGN R R

DSIGN Dp Dp

Differenza positiva 2 D1M 101M l I(cfr. Osso 14.16) D1M R R

DDlM Dp Dp

Prodotto in doppia precisione 2 ~ DPROD R Dp(cfr. Osso 14.17)

Massimo fra più argomenti con risultato ;;;.2 MAX MAXO I Idello stesso tipo degli argomenti AMAXI R R(cfr. Osso 14.18) DMAXI Dp Dp

Massimo fra più argomenti con risultato ;;;.2 AMAXO I Rdi tipo diverso (cfr. Oss. 14.18) MAXI R I

Minimo fra più argomenti con risultato ;;;.2 MIN MINO l 1dello stesso tipo degli argomenti AMINI R R(cfr. Osso 14.(8) DMINI Dp Dp

Minimo fra più argomenti con risultato ;;;.2 AMINO I Rdi tipo diverso (cfr. Osso 14.18) MINI R I

Altre funzioni intrinseche

In fig. 14.10 si descrivono le caratteristiche delle rimanenti funzioni intrinse­

che previste in F77, che in generale prevedono argomenti di tipo intero, reale e

doppia precisione e danno un risultato dello stesso tipo degli argomenti.

Figun 14.9. Funzioni intrinseche per la manipolazione dei caratteri,

Osservazioni sulla fig. 14.10

Osservazione 14.14. La funzione MOD prevede due argomenti, il secondo dei

quali deve essere diverso da zero, e calcola il resto della divisione effettuata in

aritmetica intera fra il primo ed il secondo argomento. In altri termini essa è

definita da

Descrizione della funzione Numero di Nome Tipo degli Tipo delargomenti specifico argomenti risultato

Relazione di ~ nel codice ASCII 2 LGE Cr L

Relazione di > nel codice ASCII 2 LGT Cr L

Relazione di '" nel codice ASCII 2 LLE Cr L

Relazione di < nel codice ASCII 2 LLT Cr L

Posizione della prima occorrenza di una 2 INDEX Cr Istringa a2 in una stringa al

Posizione dell'argomento nel sistema di l ICHAR Cr Icodifica usato dall'elaboratore

Carattere che occupa, nel sistema dicodifica usato dall'elaboratore, la posìzio- l CHAR I Crne espressa dall'argomento.

Lunghezza dell'argomento l LEN Cr I

268

Osservazione 14.15. La funzione SIGN prevede due argomenti e il risultato è

defini to da:

ovvero segue che per a * O SIGN (1., a) dà come risultato il valore assunto inx = a dalla funzione sgn(x) definita da:

Page 139: Fortran

SIGN (0.5, a) - SIGN (0.5, - a)

D'altra parte sgn(a) può essere calcolato, per qualunque valore di a, utiliz­

zando la funzione SIGN nel modo seguente

270

lsgn(x) = O

-l

x>O

x=O

x<O

271

Esercizi

14.1 Individuare gli errori presenti nelle seguenti istruzioni:

SUBROUTINE NEW (A, B, 0.5))

SUBROUTINE STAMPA (I, J, A(I, 1)

SUBROUTINE COPIA (X, Y, F(X»

REAL FUNCTION MEDIA (M, M +1, V)

FUNCTION INDICE (CAR (I : I))

COMPLEX FUNCTION MODULO

Osservazione 14.16. La funzione DIM prevede due argomenti, ed è definita da

DIM (al' a2) = al - a2DIM (al' a2) = O

Osservazione 14.17. La funzione DPROD calcola il prodotto in doppia precisione

fra due argomenti reali. Così, se A e B sono variabili reali e D e DD sono variabili

in doppia precisione, l'istruzione

D = DPROD (A, B)

è equivalente alla coppia di istruzioni

DD=A

D = DD * B.

Osservazione 14.18. Le funzioni MAX e MIN determinano, rispettivamente, il

massimo e il minimo fra due o più argomenti; il risultato è dello stesso tipo degli

argomenti. Esistono inoltre le funzioni AMAXO e MAXI (AMINO e MINI) che

calcolano il massimo (minimo) fra più argomenti e convertono poi il risultato a un

tipo diverso da quello degli argomenti. Queste funzioni sono state mantenute in

F77 per compatibilità con lo standard precedente F66, ma saranno probabil­

mente eliminate nella prossima versione del FORTRAN. Del resto è possibile si­

mulare queste funzioni intrinseche tramite la MAX e la MIN e le funzioni di con­

versione numerica; così, ad esempio se al' a2, ... , an sono di tipo intero, si ha

AMAXO (al' a2, .•• , an ) = REAL (MAX (al' a2, , an))

AMINO (al' a2, .. "' an ) = REAL (MIN (a" a2, , an))

mentre se a" a2, ... , an sono di tipo reale si ha

MAXI (a" a2, ... , an ) = INT (MAX (al' a2, ... , an))

MINI (a" a2, · · ", an ) = INT (MIN (al' a2, · · · , an))

Come si è già accennato nel cap. 6, in F66 non esistevano nomi generici per

le funzioni intrinseche, ma soltanto nomi specifici e inoltre molte funzioni pre­

viste in F77 non erano previste in F66 (cfr. appendice A2).

14.2 E' dato il sottoprogramma seguente

SUBROUTINE ESERC (M, MI, ALFA, BETA)

INTEGER M, MI

REAL ALFA, BETA

END

Supponendo che A e B siano variabili reali e M e N variabili intere, indicare

quali tra le istruzioni CALL seguenti sono formalmente corrette e quali

non lo sono.

CALL ESERC (M, N, A, B) .: I

CALL ESERC (M, B, A) ,1(

CALL ESERC (4, N, A, B) s {CALL ESERC (N, M, 0.5, 0.5) :. I

CALL ESERC (A, B, M, N) II (l

CALL ESERC (M, N, S, B) " (.;

14.3 E' dato un sottoprogramma FUNCTION di tipo reale e di nome EFFE

che prevede, quali argomenti muti, due variabili reali. Individuare gli even­

tuali errori formali nelle seguenti istruzioni che utilizzano EFFE, suppo­

nendo che A e B siano variabili reali e K sia una variabile intera:

IF (EFFE (A, B).GT.EFFE (O., O.)) A = EFFE (A, B)

X = EFFE (A, B) - EFFE (B, A)

B = EFFE (O; 0.5) ti )

READ *, A, B, EFFE (A, B)

A = ABS (EFFE()9, B» rI ()

EFFE (A, B) = EFFE (A, B) - 1.

PRINT *, EFFE (A) ì10

14.4 Trasformare in un sottoprogramma il programma dell'Esempio 10.9, giu­

stificando la scelta fra un sottoprogramma FUNCTION o un sottopro­

gramma SUBROUTINE.

Page 140: Fortran

(soluzioni: l e - 3)

x2-0.2001104x+0.l001l0?=0

x2 _ 2 10- 3 x + 10- 6 = O

x2 - 6 x + 34 = O

x2 - 105 x + l = O

I J

272

14.5 Scrivere un sottoprogramma che, dato un vettore reale di 100 elementi,fornisca come risultato la media aritmetica dei valori dei suoi elementi.Giustificare la scelta fra un sottoprogramma FUNCfl0N e un sottopro­gramma SUBROUTINE.

14.6 Scrivere un sottoprogramma che utilizza il sottoprogramma SOLV2 delloesempio 14.5 per calcolare le soluzioni reali o complesse delle seguentiequazioni:x:l + 2x - 3 = O

(soluzioni: 1000e 1001)

(soluzioni: 10- 3 e 10- 3)

(soluzioni: 3 + Si, 3 - Si)

(soluzioni calcolate con Il cifre:0.99999999990 105 e0.1000000000 l 10- 4)

Eseguire i calcoli suddetti utilizzando i seguenti valori di e: €M' lO €M'

100 €M' dove €M è la precisione di macchina che può essere calcolata conil sottoprogramma EPSM dell'esempio 14.13.

14.7 Spiegare il significato assunto dal sottoprogramma EPSM dell'esempio14.13 se si sostituisce la frase iniziale con le frasi

DOUBLE PRECISION FUNCfION EPSM ( )DOUBLE PRECISION A

14.8 Scrivere un sottoprogramma di tipo SUBROUTINE che, assegnato un

vettore X reale di 100 elementi e un intero N, con O< N < 100, permettadi localizzare, se esiste, il primo elemento di X diverso da zero a partire daX(N) e fornisca come risultato la posizione, LOC, di tale elemento e il suovalore, V. Il sottoprogramma deve inoltre segnalare con un opportuno valo­re di LOC il caso in cui tutti gli elementi di X a partire da X(N) siano uguali

a zero.

14.9 Scrivere un sottoprogramma che risolva il problema del precedente eser­cizio, ma fornisca in uscita soltanto il valore di LOC.

14.10 Scrivere un sottoprogramma FUNCfION che permetta di calcolare, asse­gnato il numero complesso z, il valore complesso w(z), dove

w(z) = Iz I+ (l + 3i) z

273

Scrivere inoltre un programma che utilizza il precedente sottoprogrammaper calcolare e stampare i valori di w(z) per i seguenti valori di z: 2 - 3i,S. 8 + 102 i, - 5i.

14.11 Scrivere un sottoprogramma che, assegnata una stringa X di 60 caratteri,fornisca in uscita una stringa W costituita dai caratteri di X diversi dal ca­rattere blank, e il numero di questi caratteri. Scrivere inoltre un programmache utilizzi il sottoprogramma suddetto avendo come dato la stringa:

'MATTEOvHAvFATTOvUNAvCORSAvEDvORAvHA vlLv RESPIROvAFFANNOSOvvvv'

14.12 Individuare quali fra le seguenti frasi che definiscono una funzione sono

sintatticamente corrette:

F(A, B, C) = (A + B + C)/3.F(A, B, C, 3) = (A + B + C)/3

F = (A + B + C)/3

14.13 Individuare gli errori contenuti nei seguenti riferimenti a funzioni intrin­seche, supponendo che R, l, C siano variabili di tipo reale, intero e com­

plesso rispettivamente.

SQRT(I)

ABS (CMPLX(R, I»CMPLX (AIMAG(R»NINT (C)

MOD (R, NINT(R»EXP (lNT(R».

14.14 Scrivere un sottoprogramma che consenta di calcolare il prodotto scalarefra due vettori reali di N elementi, con N ~ SO, e che utilizzi la funzioneintrinseca DPROD per eseguire i prodotti in doppia precisione (cfr. esem­pio Il.22).

Page 141: Fortran

J

15Argomenti mutied argomenti attuali

15.1. Associazione tra argomenti muti ed argomenti attuali

L'attivazione di un sottoprogramma e la sua esecuzione presuppongono uno

scambio di informazioni tra unità di programma chiamante e sottoprogramma.

Questo scambio può avvenire attraverso la lista degli argomenti muti in quanto

ad essa è associata quella degli argomenti attuali in modo tale che, durante l'ese­cuzione del sottoprogramma, ogni riferimento ad un argomento muto. è di fatto,

un riferimento al corrispondente argomento attuale. Al momento della chiamata

di un sottoprogramma viene infatti trasmesso per ciascun argomento muto l'indi­

rizzo del corrispondente argomento attuale e diventano pertanto direttamente

utilizzabili dal sottoprogramma gli indirizzi delle locazioni in cui si trovano me-

1morizzati i valori degli argomenti attuali. Gli argomenti muti di Wl sottopro- .gramma sono quindi completamente definiti soltanto al momento della attiva­zione del sottoprogramma quando ognuno di essi identifica la stessa locazione dimemoria del corrispondente argomento attuale. La corretta esecuzione di un sot- .

toprogramma è pertanto subordinata ad una corretta corrispondenza tra gli argo-menti muti e quelli attuali; eventuali errori non sono generalmente segnalati dalsistema e si manifestano in fase di esecuzione con risultati del tutto inattendibili

che provocano talvolta l'interruzione del programma. Si osservi che gli errori

commessi nella associazione degli argomenti non possono essere segnalati durantela compilazione in quanto ogni unità di programma è compilata in modo autono­

mo e separatamente da tutte le altre.

15.2. Le variabili non dimensionate come argomenti muti

Quando un argomento muto è il nome di una variabile non dimensionata adesso può corrispondere, nella lista degli argomenti attuali, una variabile, un ele­mento di variabile dimensionata, una costante oppure. più in generale, un'espres­sione. In ogni caso l'argomento attuale deve essere dello stesso tipo di quellomuto.

Page 142: Fortran

277276

Esempio 15.1. Sia ESEMP un sottoprogramma definito da:

SUBROUTINE ESEMP (ARG, N)

con ARG ed N nomi di variabile rispettivamente di tipo reale ed intero. Suppo­

nendo che nell'unità di programma chiamante X identifichi una variabile reale,

Y un vettore reale, L una variabile intera ed M una matrice intera, il sottopro­

gramma ESEMP è correttamente utilizzato dalle frasi:

CALL ESEMP(X, L)CALL ESEMP(X, M(I, 2))CALL ESEMP(Y(3), L + lO)CALL ESEMP(L • Y(2)/X, 12)

mentre sono sbagliate le seguenti istruzioni:

ANG = TETA(Y) + TETA (0.5 * H)

richiede due esecuzioni del sottoprogramma TETA: la prima avviene associando

all'argomento muto X quello attuale Y, la seconda associando ad X la locazione

che contiene il valore dell'espressione 0.5 • H. Anche la frase

ANG = TETA (TETA(Y) + H)

~imPlica due esecuzioni del sottoprogramma TETA: la prima avviene usando l'in­

! diriz~o di Y e l~ seconda usando l'.indiriz~o della locazione nella quale è memoriz­

zato 11 valore di TETA (Y) + H. SI osservi che questo modo di utilizzare un sotto­

programma di tipo FUNCfION non è ricorsivo.

Esempio 15.3. Sia SOMMA un sottoprogramma definito da:

SUBROUTINE SOMMA (A, B, C)

lI

, iI '

f

CALL ESEMP(L, X)CALL ESEMP(X, 1.05)CALL ESEMP(Y(3), X + lO)CALL ESEMP(M(l, 2). L, 12)

con A, B e C nomi di variabili reali. Supponendo che A e B siano argomenti

di ingresso e che C sia di uscita, l'esecuzione della frase

CALL SOMMA (X, X, Y)

permette di associare A e B alla stessa locazione X e C alla locazione Y; sarebbe

invece sbagliato scrivere

15.3. Le variabili dimensionate come argomenti muti

Quando un argomento muto è il nome di una variabile dimensionata, ad esso

deve corrispondere come argomento attuale un nome di variabile dimensionata

oppure un nome di elemento di variabile dimensionata. Ricordiamo che all'in­

terno del sottoprogramma il nome dell'argomento muto deve comparire in una

opportuna frase di specificazione che ha come unico effetto quello di indicare al

compilatore che l'argomento è una variabile dimensionata; 'inoltre i nomi degli

elementi dell'argomento muto devono essere utilizzati nel sottoprogramma coe­

rentemente con la specificazione fatta. Anche in questo caso, l'esecuzione del

sottoprogramma avviene utilizzando per l'argomento muto le locazioni di memo­

ria riservate all'argomento attuale dall'unità di programma chiamante, in quanto

l'associazione tra l'argomento muto e quello attuale avviene mediante l'indirizzo

dell'argomento attuale. Più precisamente, l'indirizzo del primo elemento dell'ar-

;I . CALL SOMMA (X, Y, Xl Il/i1111 quanto alla stessa locazione farebbero riferimento sia un argomento di ingresso

che quello di uscita.

Esempio 15.2. Sia TETA un sottoprogramma definito dalla frase:

dove X indica un nome di variabile reale. L'esecuzione dell'istruzione

REAL FUNCfION TETA (X)

Va sottolineato che ad ogni argomento muto di uscita deve corrispondere

come argomento attuale una variabile oppure un elemento di variabile dimensio- Inata. In altri termini una costante o una espressione non devono essere usate i A

come argomento attuale in corrispondenza di un argomento muto il cui valore v

sia definito oppure modificato nel corpo del sottoprogramma. Infatti, se l'argo­

mento attuale è una costante, qualunque modificazione del corrispondente argo­

mento muto provoca un cambiamento del valore della costante che invece deve

rimanere inalterato durante tutta l'esecuzione del programma. Il divieto di utiliz­

zare un'espressione in corrispondenza di un argomento muto di uscita deriva, in­

vece, dal fatto che l'associazione tra l'espressione ed il corrispondente argomento

muto avviene mediante l'indirizzo della locazione nella quale, al momento della

chiamata del sottoprogramma, è memorizzato il valore dell'espressione. Questo

indirizzo viene trasmesso al sottoprogramma ma non è noto all'unità di program­

ma attivante che, pertanto, non lo può utilizzare. Si osservi infine che, se due 'j',argomenti attuali coincidono. nessuno dei corrispondenti argomenti muti può ['

essere un argomento di uscita.

Page 143: Fortran

278

gomento muto coincide con quello del primo elemento dell'argomento attualese

questo è il nome di una variabile dimensionata; se invece il parametro attuale è un

elemento di variabile dimensionata, il suo indirizzo viene utilizzato dal sottopro­

grarnma come indirizzo del primo elemento del parametro muto. In ogni caso, gli

indirizzi dei successivi elementi dell'argomento muto vengono determinati a

partire dall'indirizzo del primo elemento in base al numero di dimensioni e alle

limitazioni di ciascuna dimensione dell'argomento muto secondo le modalità

viste nel cap. II.

Esempio 15.4. Il seguente sottoprogramma, SOM, permette di sommare i quattro

elementi di un vettore V con gli elementi di posto dispari di un vettore W di am­

piezza IO. Il risultato viene memorizzato nella variabile reale A.

SU8ROUTINE SOM (V, W, A)REAL V(4), W(IO)A=Q.DOlO, 1=1,4A = A + V(I)

IO CONTINUEDO 20 1=1,10,2A = A + W(I)

20 CONTINUERETURNEND

Questo sottoprogramma può essere correttamente utilizzato nel modo seguente:

REAL X(IO), Y(20)

CALL SOM (X, Y, Al)CALL SOM (X(6), Y(II), A2)CALL SOM (Y, X, A3)

Dopo l'esecuzione di queste frasi

A I contiene:

1l

279

muti V e W sono rispettivamente associati a X ed Y mediante l'indirizzo di X( I)

ed Yt l ): con l'esecuzione della seconda chiamata il primo elemento di V è asso­ciato all'elemento X(6) ed il primo elemento di W a Yf l l ): infine, l'ultima attiva­

zione del sottoprogramma avviene associando V ad Y mediante l'indirizzo di Y( I)

e W ad X mediante l'indirizzo di X( I).

Si osservi che quando un argomento muto ed il corrispondente argomento

"' attuale sono nomi di variabili dimensionate, l'argomento attuale deve avere am­i piezza maggiore o uguale a quella dell'argomento muto, ovvero il numero totale

degli elementi dell'argomento muto non deve superare quello del corrispondente

!argomento attuale. Quando l'argomento attuale è un elemento di variabile dimen­

l' i sionata, l'ampiezza dell'argomento muto non deve superare il numero di elementi

J\ di tale variabile compresi fra l'elemento specificato come argomento attuale e

l'ultimo.

.4Esempio 15.5. Si vogliono sommare gli elementi di una matrice di 2 righe e 2

colonne con quelli di posto dispari della terza colonna di una matrice B di IOrighe e 3 colonne.

Questo problema può essere risolto utilizzando il sottoprogramrna SOM

dell'esempio 15.4 nel modo seguente:

REAL A(2, 2), 8(10,3)

CALL SOM (A, B(1,3),S)

AI momento dell'attivazione del sottoprogramma il primo elemento dell'ar­

gomento muto V è associato al primo elemento della matrice A mentre il primo

elemento di W è associato al primo elemento della terza colonna di B; infine

l'argomento muto di uscita A è associato ad S. Durante l'esecuzione del sotto­

programma gli elementi degli argomenti muti V e W sono associati agli elementi

dei corrispondenti argomenti attuali nel modo seguente:

X(l) + X(2) + X(3) + X(4) + Y(l) + Y(3) + Y(5) + Y(7) + Y(9)

A2 contiene:

X(6) + X(7) + X(8) + X(9) + Y(lI) + Y(l3) + Y(l5) + Y(l7) + Y(l9)

V(I)

A(I,I)

V(4)

A(2,2)

A3 contiene:

Y(l) + Y(2) + Y(3) + Y(4) + X(1) + X(3) + X(5) + X(7) + X(9)

Infatti, al momento della prima chiamata del sottoprogramma gli argomenti

W(l) W(2) W(3) W(4) W(5) W(6) W(7) W(8) W(9) W(lO)

8(l,3) 8(2,3) 8(3,3) B(4,3) 8(5,3) B(6,3) 8(7,3) 8(8,3) 8(9,3) B(IO,3)

Page 144: Fortran

280

Esempio 15.6. Supponiamo di utilizzare ancora il sottoprogramma SOM del­

l'esempio 15.4 nel modo seguente:

REAL A(3, 3),8(3, lO)

CALL SOM(A,8(1,3),S)

In questo caso, gli elementi del parametro muto V corrispondono a quelli del

parametro attuale A nel modo seguente:

V(l) V(2) V(3) V(4)

A(l,l) A(2,1) A(3,1) A(1,2)

mentre gli elementi di W e quelli di B si corrispondono nel modo seguente:

W(1) W(2) I W(3) W(4) W(5) W(6) W(7) W(8) W(9) W(10)

8(1,3) 8(2,3) 8(3,3) 8(1,4) 8(2,4) 8(3,4) 8(1,5) 8(2,5) B(3,5) 8(1,6)

15.4. Dimensionamento variabile e dimensionamento indefinito

In un sottoprogramma è possibile specificare le dimensioni di un argomento

muto mediante una particolare forma di dichiaratore di dimensione detta dichia­

ratore di dimensione variabile. Un dichiaratore di dimensione è detto dichiaratore

di dimensione variabile se contiene un'espressione intera in cui compare almeno.

un nome di variabile; questo nome di variabile deve far parte della lista degli argo­

menti muti o di un blocco COMMON (cfr. cap. 16). Nel ~~g~i!(}':!I!,!jJ~edichia­

rativa nella quale compare un dichiaratore di dimensione variabile verr~Q~tta fra­

se di dimensionamento variabile; essa deve precedere tutte le frasi eseguibili del

corpo del sottoprogramma ma deve essere preceduta da tutte le eventuali frasi di

specificazione che interessano le variabili intere usate nei dichiara tori. Sono per­

tanto esempi di corretta utilizzazione del dimensionamento variabile i seguenti:

SU8ROUTINE ESI (V, A, N)REAL V(N), A(N, N)

SUBROUTlNE ES2 (V, R, S)INTEGER R, SREAL V(R: S)

REAL FUNCTION ES3 (V, M, N)REAL V(M + N • 5)

j

281

REAL FUNCTION ES4 (V, W, A, N)DIMENSION A(N, 7), W(19, N + I), V(O : N - 3)

L'ampiezza delle dimensioni specificate con i dichiaratori di dimensione varia­bile è determinata al momento dell'attivazione del sottoprogramma. In questa

fase infatti viene definito il valore delle variabili intere usate nei dichiaratori e so­no valutate le espressioni che compaiono nei dichiaratori stessi. Il valore dei di-

jChiaratOri di dimensione variabile resta inalterato durante tutta l'esecuzione del I

l sottoprogramma anche se il contenuto delle variabili intere usate nei dichiaratori Ltviene modificato.

Esempio 15.7. Supponiamo che

SUBROUTlNE SU81 (V, W, A, NV, NW)REAL V(NV), W(NV + NW + 2)

siano le frasi iniziali del sottoprogramma SUB 1. In esse V e W indicano due vet­tori reali le cui dimensioni sono specificate mediante gli argomenti muti NV edNW. Se, al momento della attivazione di SUB l, gli argomenti attuali corrispon­

denti ad NV ed NW valgono entrambi 15, allora durante l'esecuzione di SUBI ilvettore V viene considerato di ampiezza 15 e W di ampiezza 32; se invece, al mo­

mento della chiamata di SUB l, NV contiene il valore lO ed NW il valore - 5,

il sottoprogramma viene eseguito come se fosse stata usata la specificazione.

REAL V( lO), W(7).

Esempio 15.8. Per calcolare l'elemento massimo di un vettore X di N elementi

si può usare il seguente sottoprogramma:

REAL FUNCTION MMV(X, N)INTEGER NREAL X(N)MMV = X(l)DO 200 1 = 2, NIF (X(I).GT.MMV) MMV = X(l)

200 CONTINUERETURNEND

E' possibile utilizzare questo sottoprogramma per calcolare i massimi elementi

delle colonne di una o più matrici reali. Supponendo che A sia una matrice di l Orighe e 5 colonne e che B sia una matrice di 20 righe e 40 colonne, il seguenteprogramma permette di definire i valori dei 45 elementi di un vettore V memoriz-

,i

I11

Page 145: Fortran

282

zando nei primi S, gli elementi massimi di ciascuna colonna di A e, nei restanti 40,

gli elementi massimi di ogni colonna di B.

PROGRAM USOMMVREAL A(lO, 5), B(20, 40), V(45), MMVNRA = lONCA=5NRB = 20NCB =40READ -. A, BDO 20 I = I, NCAV(I) = MMV(A(l, I), NRA)

20 CONTINUEDO 30 I = I, NCBV(NCA + I) = MMV(B( l, I), NRB)

30 CONTINUEPRINT -. VSTOPEND

All'interno del primo ciclo-DO il sottoprogramma MMV viene attivato NCA

volte ed ogni attivazione avviene associando il primo elemento di una colonna di

A al primo elemento dell'argomento muto X la cui ampiezza è determinata dal

valore, lO, di NRA. All'interno del secondo ciclo-DO il sottoprogramma è invece

attivato NCB volte: ogni volta il primo elemento di una colonna di B è associato

al primo elemento dell'argomento muto X la cui ampiezza, determinata dal valore

di NRB, è uguale a 20. Si osservi che, per una corretta utilizzazione del sottopro­

grarnma, è indispensabile specificare nell'unità di programma chiamante che

MMV è di tipo reale.

Esempio 15.9. Siano xl' x2' .. " xn le componenti di un vettore x; indicata conIl la quantità

Il = max I x·1 'l" i" n I

la norma euclidea di x, ~ x Ib, può essere calcolata nel modo seguente:

se Il = O

se Il =1= O

Un sottoprogramma che permette di calcolare, dati x ed n, la norma Il x 112 è

1I

283

allora il seguente:

REAL FUNCTION NORMA2 (X, N)C NORMA2 INDICA LA NORMA EUCLIDEA DEL VETTORE XC N INDICA IL NUMERO DI ELEMENTI DI X

REAL MI, X(N)C CALCOLO DEL MASSIMO FRA I VALORI ASSOLUTIC DEGLI ELEMENTI DI X

MI = ABS(X(I»DO IO 1= 2, NIF (MI.LT.ABS(X(I») MI= ABS(X(I»

IO CONTINUENORMA2 = o.IF(MI.EQ.O.) RETURNDO 20 I = l, NNORMA2 = NORMA2 + (X(I)/MI) ** 2

20 CONTINUENORMA2 = MI * SQRT (NORMA2)RETURNEND

Il sottoprogramma NORMA2 può essere utilizzato per calcolare la quantità

dove c(i) indica la i-esima colonna di una matrice A di m righe ed n colonne. Sup­

ponendo m = lO ed n = S, SC può essere calcolato dal programma seguente:

PROGRAM V ALSCREAL A(lO, 5), NORMA2READ *, AM=ION=5SC =0.DO IO I = I, NSC = se + NORMA2 (A(I, I), M)

IO CONTINUEPRINT -. 'QUANTITA"VCALCOLATAv', SCSTOPEND

Questo programma deve essere notevolmente modificato se, invece della quan­tità sc' si vuoI calcolare

sr = t 1/r(i) 112i= 1

Page 146: Fortran

284

dove r(i) indica la i-esima riga della matrice A. Si considerino infatti le seguenti

istruZIOI1I, analoghe a quelle usate nel programma VALSC:

SR =0.DO lO I = l, MSR = SR + NORMA2 (A(I, l), N)

lO CONTINUE

L'esecuzione di queste istruzioni prevede che, per ogni valore di I, il primo ele­

mento dell'argomento muto X abbia lo stesso indirizzo di A(l, l) e che l'ampiezzadi X sia uguale a S. Durante l'esecuzione del sottoprogramma, gli elementi di Xsono quindi associati ad A(l, l) e alle quattro locazioni di memoria ad esso con-

secutive nel modo seguente:

X(l)

A(I, l)

Pertanto, per ogni valore di i, il sottoprogramma NORMA2 fornisce la quantitài+ 4 5

(I: a~ l )1/ 2 e non quella utile per il calcolo di sr che è data da (. I: a; /1 2. Af-

j~ i J. J= l •finché il problema possa essere correttamente risolto occorre che gli elementi diciascuna riga di A vengano memorizzati, prima della chiamata del sottoprogram­ma, in locazioni consecutive di memoria. Per questo si utilizza un vettore, RIGA,nel quale vengono memorizzati tutti gli elementi della i-esima riga di A. Questovettore costituisce l'argomento attuale che aeve essere associato a quello mutoX per poter calcolare la norma euclidea della i-esima riga di A. Il programma può

essere allora il seguente:

PROGRAM VALSRREAL A(lO, 5), NORMA2,RIGA (5)

READ -. AM=1ON = 5SR=O.DO 20 l = l, MDO lO J = l, N

lO RIGA (1) = A(I, J)SR = SR + NORMA2 (RIGA, N)

20 CONTINUEPRINT -. 'VALOREvCALCOLATOvSR =', SRSTOPEND

285

Dimensionamento variabile per argomenti muti con due o più dimensioni

Per chiarire come deve essere usato il dimensionamento variabile per argomenti

muti con due o più dimensioni, consideriamo il seguente esempio.

Esempio 15.10. Sia MATRIX un sottoprogramma definito dalla frase iniziale:

SUBROUTINE MATRIX (A, N, M. B)

dove A, N ed M sono gli argomenti di ingresso e B è quello di uscita e, inoltre, A

è una matrice specificata da

REAL A(N, M)

Sia PROGI un programma che utilizza MATRIX nel modo seguente:

PROGRAM PROGIREAL X(3, 4), Y(2, 3)READ *, X, YNR=3NC =4CALL MATRIX (X, NR, NC,BI)CALL MATRIX (Y, NR - l, NC - l, B2)

Al momento della prima attivazione del sottoprogramma, l'argomento muto

A è associato a quello attuale X mediante l'indirizzo di X( l, l) e inoltre N è asso­ciato ad NR, M a NC e B a Bl. Per effetto della prima frase CALL si crea quin­

di tra gli elementi di A e quelli di X una associazione per la quale ogni elemen­

to A(I, 1) nel sottoprogramma corrisponde all'elemento X(l, 1) del program­

ma principale per ogni valore di I, l ~ 1 ~ 3, ed ogni valore di J, l ~ J ~ 4. Al

momento della seconda chiamata, l'argomento muto A è associato ad Y mediante

l'indirizzo di Y( l, l), la variabile N è associata alla locazione che contiene il

valore dell'espressione NR - l, la variabile M è associata alla locazione che con­

tiene il valore di NC - 1 e B è associata a B2. L'esecuzione della seconda frase

CALL stabilisce pertanto che ogni elemento A(I, J) corrisponde a Y(l, J) per ogni

I compreso fra l e 2 e J compreso fra 1 e 3.Esaminiamo ora come avviene la associazione tra argomenti muti ed argomenti

attuali supponendo di usare il sottoprogramma MATRIX con la seguente unità

di programma chiamante:

'Ii,

, IlI l

I

Page 147: Fortran

·ìlI

286

PROGRAM PROG2REAL X(3,4)READ -, XNR=3NC =4CALL MATRIX (X, NR, NC, BI)CALL MATRIX (X, NC, NR, B2)CALL MATRIX (X, NR - l, NC + 2, B3)CALL MATRIX (X, NR, NR, B4)

La corrispondenza che si crea tra gli elementi dell'argomento muto A e quelli

dell'argomento attuale X con l'esecuzione delle quattro frasi CALL presenti in

PROG2 è la seguente:

TI

287

gli elementi dell'argomento muto coincidono con quelli che individuano gli ele­menti dell'argomento attuale soltanto se il numero di righe dell'argomento mutocoincide con il numero di righe specificato per l'argomento attuale nell'unità di

programma chiamante.

Esempio 15.11. II seguente sottoprogramma DEFMAT permette di risolvere il

seguente problema: dato n, determinare gli elementi h(n) di una matrice quadrata1.1

Hn di ordine n definiti da

n se i = j

h~nJ = n/(j + 1) se i > j i, j = 1,2, ... , nr.j

(i - 1)/0 - 1) se i <j

Prima CALL:

Seconda CALL:

xn.n X(2,l) X(3,1) X(l,2) X(2,2) X(3,2) X(l,3) X(2,3) X(3,3) X(l,4) X(2,4) X(3,4)

A(l,l) A(2,l) A(3,l) A(I,2) -\(2,2) A(3,2) A(l,3) A(2,3) A(3,3) A(l,4) A(2,4) A(3,4)

xci, l) X(2,l) X(3,l) X(I,2) X(2,2) X(3,2) X(l,3) X(2,3) X(3,3) X(1,4) X(2,4) lX(3,4)

A(1,I) A(2,1) A(3,l) A(4,1) A(l,2) A(2,2) A(3,2) A(4,2) A(l,3) A(2,3) A(3,3) IA(4,3)

SUBROUTINE DEFMAT (H, NR, N)REAL H(NR, N)DO 20 1= 1, NDO 20 J = I, N1F (I.EQ.J) THEN

H(I, J) = NELSE IF(I.GT.J) THEN

H(I, J) = N/(1 + 1.)ELSE

H(I, J) =(1- 1.)/(1 - 1.)ENDIF

20 CONTINUERETURNEND

II significato degli argomenti muti di DEFMAT è il seguente: H è una matrice

reale che contiene, al termine dell'esecuzione del sottoprogramma, la matrice Hn ;

NR ed N sono argomenti di ingresso, il primo dei quali serve per specificare ilnumero di righe di H nel descrittore di dimensione variabile e il secondo rappre­

senta l'ordine n della matrice Hn di cui si devono definire gli elementi.

Consideriamo ora il seguente programma principale, ATTIVA, nel quale il sot­toprogramma DEFMAT viene utilizzato 5 volte durante l'esecuzione del ciclo-DO

per calcolare successivamente le matrici Hn, con n = 2, 4,6, 8, IO e memorizzarle

nelle stesse locazioni di memoria riservate alla matrice di ordine maggiore. Si noti

che, durante ogni esecuzione di DEFMAT, gli indici che individuano gli elementi

dell'argomento muto H e gli elementi dell'argomento attuale ad esso associato

concidono. Questa coincidenza di indici è dovuta al fatto che ad ogni attivazione

il valore dell'argomento attuale NR è uguale al numero di righe specificato per

l'argomento attuale H nel programma ATTIVA.

X(3,4)

A(2,6)

X(1.1)

X(1,1) X(2,1) X(3,l) X(l,2) X(2,2) X(3,2) X(l,3)

A(l,l) A(2.l) A(l,2) -\(2,2) A(l,3) A(2,3) A(1,4)

A(1,1)

L'esempio precedente mette in evidenza che, quando il numero di righe di una

matrice usata come argomento muto non coincide con quello specificato per il

corrispondente argomento attuale, alcuni elementi delI'argomento muto risul­

tano associati ad elementi dell'argomento attuale individuati da indici diversi.

In altri termini, quando si utilizza un sottoprogramma che prevede tra gli argo­menti muti una matrice, si deve tener presente che gli indici che individuano

Terza CALL:

Quarta CALL:

Page 148: Fortran

288

PROGRAM ATTIVAREAL H(lO, lO)NR= lODO lO N = 2, 10,2PRINT., 'ORDINE DELLA MATRICE N =', NCALL DEFMAT (H, NR, N)DO lO I = l, NWRITE (.,1000) (H(l, J), J = l, N)

lO CONTINUESTOP

1000 FORMAT (lO (IX, E12.S»END

Le osservazioni fatte per le matrici valgono anche quando un argomento muto

ha più di due dimensioni. Infatti, se m è il numero di dimensioni, gli indici che in­

dividuano gli elementi dell'argomento muto coincidono con quelli degli elementi

dell'argomento attuale associato, soltanto se al momento dell'attivazione i valori

dei dichiaratori delle prime (m - 1) dimensioni dell'argomento muto coincidono

con quelli fissati per l'argomento attuale nell'unità di programma chiamante.

In questo caso l'ampiezza dell'ultima dimensione dell'argomento muto non deve

superare quella dell'ultima dimensione dell'argomento attuale.Il dimensionamento vanabile era previsto anche in F66 ma erano ammessi

come dichiaratori di dimensione variabile soltanto nomi di variabili intere facenti

parte della lista degli argomenti muti o di un blocco COMMON.

Dimensionamento indefinito

In F77 è prevista una ulteriore forma particolare di dichiaratore di dimensione

per un argomento muto, detta dichiaratore di dimensione indefinita. Si dice che

un argomento muto ha dimensionamento indefinito se l'ultimo dichiaratore di

dimensione è un asterisco. Sono esempi di uso del dimensionamento indefinito

le frasi

REAL X(*), B(10, *), A(M, *)DIMENSION Y(- 5 : N, *), Z(N + M, L, *)

Se un argomento muto ha dimensionamento indefinito, la sua ampiezza non

viene calcolata al momento dell'attivazione del sottoprogramma la cui esecuzione

avviene quindi ignorando l'ampiezza dell'argomento muto; per q~~s!O!1l()!!VQ, un

parametro muto che ha dimensionamento indefinito non può essere usato nel cor­

po del sottoprogramma in frasi la cui esecuzione richiede la conoscenza esplicita

della sua ampiezza. Così, per esempio, la frase:

PRINT *, A

289

non può essere usata in un sottoprogramma se A è una matrice che compare nella

lista degli argomenti muti ed ha dimensionamento indefinito.

Il dimensionamento indefinito non è previsto in F66.

15.5. Argomenti muti di tipo carattere

Se un argomento muto di un sottoprogramma è di tipo carattere, il suo tipo e

la sua lunghezza devono essere opportunamente specificati all'interno del sotto­programma.

Se l'argomento muto è una variabile carattere, il corrispondente argomento at­

tuale può essere una costante, una variabile, una sottostringa, un elemento di

variabile dimensionata, oppure un'espressione carattere. In ogni caso la lunghezzadell'argomento muto non deve superare quella dell'argomento attuale. Se la lun­

ghezza ~ dell'argomento muto è uguale a quella dell'argomento attuale, al momen­

to dell'attivazione del sottoprogramma l'argomento muto è associato alla stringaidentificata dall'argomento attuale mediante !'indirizzo dell'unità di memoria

in cui è memorizzato il primo carattere dell'argomento attuale. Se invece la lun­

ghezza ~ dell'argomento muto è inferiore a quella dell'argomento attuale, l'argo­

mento muto è associato alla sottostringa costituita dai primi ~ caratteri dell'argo­mento attuale.

Esempio 15.12. Indicate con LI ed L2 due lettere dell'alfabeto, il sottoprogram­

ma seguente permette di stabilire se la stringa di lunghezza 8 rappresentata dal­

l'argomento muto DATO inizia con LI e termina con L2. Il sottoprogramma

infatti determina il valore di una variabile logica, IND, il cui valore è «vero» sol­

tanto se DATO inizia con LI e termina con L2. Nel caso in cui IND sia «falso»,

il sottoprogramma memorizza il carattere iniziale e quello finale di DATO in LIed L2 rispettivamente.

SUBROUTlNE INFIN (DATO, IND, LI, L2)LOGICAL INDCHARACTER DATO. 8, LI • l, L2 • lN=8IF (DATO (I: l ).EQ.Ll.AND.DATO (N: N).EQ.L2) THEN

IND= .TRUE.ELSE

IND = .FALSE.LI = DATO (l:l)L2 = DATO (N:N)

ENDIFRETURNEND

II >

III

II"

Page 149: Fortran

292

Sarebbe invece sbagliata l'istruzione

CALL INFIN (X//A, IND, IN, FIN)

in quanto in essa figura come argomento attuale un'espressione carattere nella

quale un operando, X, è un argomento muto di lunghezza indefinita.

Se un argomento muto è una variabile dimensionata di tipo carattere, l'argo­

mento attuale ad esso corrispondente deve essere di tipo carattere e può essere

il nome di una variabile dimensionata, di un elemento di variabile dimensionata,

di una sottostringa di un elemento di variabile dimensionata. In ogni caso, l'asso­

ciazione tra l'argomento muto e quello attuale viene fatta mediante l'indirizzo

dell'unità di memoria in cui è memorizzato il primo carattere dell'argomento

attuale. Si osservi che quando un argomento è una variabile dimensionata carat­

tere esso individua unità di memoria consecutive in quanto l'ultimo carattere di

ogni elemento è immediatamente seguito dal primo carattere dell'elemento suc­

cessivo. Il numero di unità di memoria carattere individuate da un argomento

costituisce la sua lunghezza complessiva. In particolare, se un argomento attualeè il nome di un elemento o di una sottostringa di un elemento di una variabile

dimensionata, la sua lunghezza complessiva è costituita dal numero di caratteri

compresi tra il primo carattere dell'elemento o della sottostringa specificati e

l'ultimo carattere dell'ultimo elemento.La lunghezza dei singoli elementi di un argomento muto di tipo carattere può

differire da quella degli elementi dell'argomento attuale ma la sua lunghezza com­

plessiva, determinata in base alla specificazione presente nel sottoprogramma, non

deve superare quella dell'argomento attuale.

15.6. I nomi di sottoprogrammi come argomenti muti. Le frasi EXTERNAL e

INTRINSIC

Un argomento muto di un sottoprogramma può essere il nome di unaltr() sot­

toprogramma e, in questo caso, il corrispondente argomento attuale deve essere,

a sua volta, il nome di un sottoprogramma. Così, per esempio, se il nome, NOME,

di un sottoprogramma fa parte della lista degli argomenti muti di un altro sotto­

programma, CHIAMA, ogni riferimento a NOME all'interno di CHIAMA equivale

ad un riferimento al sottoprogramma il cui nome è specificato come argomento

attuale in corrispondenza di NOME. Per poter realizzare l'associazione tra il

nome del sottoprogramma presente nella lista degli argomenti muti e quello spe­

cificato come argomento attuale, quest'ultimo deve apparire in una opportuna

frase dichiarativa nell'unità di programma chiamante.Per semplicità di esposizione nel seguito useremo il termine sottoprogramma

293

esterno per indicare un sottoprogramma SUBROUTINE oppure FUNCTION.

La frase EXTERNAL

L'istruzione dichiarativa EXTERNAL permette di individuare, in una lista di

argomenti, i nomi di sottoprogrammi esterni; essa ha la forma seguente:

EXTERNA L lista

dove:• EXTERNAL è la parola chiave che identifica la frase;

• lista è una lista di uno o più nomi di sottoprogrammi di tipo SUBROUTINE,FUNCTION, BLOCK DATA. Se la lista è costituita da più nomi, essi sono separa­

ti da virgole.Ogni nome di sottoprogramma che compare nella lista di una frase EXTERNAL

può essere usato come argomento attuale nella stessa unità di programma in

cui compare la frase EXTERNAL. D'altra parte, se un nome di sottoprogramma

esterno fa parte di una lista di argomenti attuali esso deve comparire. nella stessa

unità di programma, in una frase EXTERNAL. Per esempio la frase:

EXTERNAL FUNZ, F

indica che i nomi FUNZ ed F sono nomi di sottoprogrammi esterni e che essi

possono essere usati come argomenti attuali nell'unità di programma che contiene

questa frase.Si osservi che~Uquando un nome simbolico compare in un'istruzione EXTERNAL

esso è interpretato come il nome di un sottoprogramma esterno; in particola­

re, se la lista di una frase EXTERNAL comprende il nome di una funzione in­

trinseca, quel nome individua un sottoprogramma esterno diverso dalla funzio­

ne intrinseca. Così la specificazione

EXTERNAL SQRT

serve per indicare che nell'unità di programma in cui essa compare SQRT è il no­

me di un sottoprogramma esterno diverso dalla omonima funzione intrinseca. E'

evidente che in questa unità di programma non è possibile utilizzare la funzione

intrinseca SQRT perché ogni riferimento ad SQRT viene interpretato come un ri­

ferimento al sottoprogramma esterno e non alla funzione intrinseca.Si noti che in F66 il nome di una funzione intrinseca non poteva essere usato

come nome di un sottoprogramma esterno e la sua presenza nella lista di una frase

EXTERNAL serviva soltanto a specificare che esso poteva essere usato come

argomento attuale nella stessa unità di programma.

Esempio 15.15. Sia f(x) una funzione reale definita per x ~ xo' con f(xo) * 0,

e sia € > O una quantità assegnata. Supponendo noti i valori xo' h, n si considera-

, :\I I

I ·1,~

Page 150: Fortran

. I

290

Questo sottoprogramma può essere usato per determinare il primo e l'ultimocarattere di stringhe di lunghezza 8, come nel seguente esempio:

CHARACTER IN, FIN, VI .8,LOGICAL INDIN='G'FIN = 'E'VI = 'GIUSEPPE'CALL INFIN (VI, IND, IN, FIN)

L'argomento muto DATO corrisponde all'argomento attuale VI, ed entrambisono di tipo carattere e lunghezza 8; pertanto, durante l'esecuzione del sotto­programma il valore di DATO è 'GIUSEPPE'. Gli argomenti attuali IND, IN, FINcorrispondono rispettivamente agli argomenti muti IND, LI ed L2. Siccome ivalori in ingresso di LI ed L2 sono 'G' ed 'E', dopo l'esecuzione del sottoprograrn­

ma IND contiene il valore .TRUE. e i contenuti di IN e FIN sono immutati.Sia ora V2 una variabile carattere di lunghezza 14 contenente la stringa di carat­teri 'MARIA v GELTRUDE' . Se IN e FIN valgono 'G' ed 'E' rispettivamente,

dopo l'esecuzione della frase

CALL INFIN (V2(7:), IND, IN, FIN)

i valori di IND, IN e FIN sono, nell'ordine, .TRUE., 'G' ed 'E', mentre essi di­

ventano .FALSE., 'M'ed 'E' se viene eseguita la frase

CALL INFIN (V2, IND, IN, FIN)

Infatti nel primo caso l'argomento muto DATO viene associato alla sottostringaV2(7:) che vale 'GELTRUDE', mentre nel secondo caso esso viene associatoalla sottostringa costituita dai primi 8 caratteri di V2, ovvero a 'MARIA vGE'.

Si osservi che non sarebbe corretto utilizzare il sottoprogramma INFIN asso­ciando a DATO una stringa di lunghezza inferiore a 8. Per esempio è sbagliata lafrase:

CALL INFIN ('FRANCO', IND, IN, FIN)

in quanto l'argomento attuale corrispondente a DATO è la stringa 'FRANCO' dilunghezza 6.

L'esempio precedente mette in evidenza che l'obbligo di specificare nel corpodel sottoprogramma la lunghezza degli argomenti di tipo carattere può limitare lepossibilità di utilizzazione del sottoprogramma stesso. Per questo è prevista lapossibilità di definire la lunghezza di un argomento muto di tipo carattere me­diante lo specificatore di lunghezza indefinita (.); in questo modo la lunghezza

291

di un argomento muto viene definita soltanto al momento della chiamata delsottoprogramma quando viene posta uguale a quella dell'argomento attualecorrispondente.

Esempio 15.13. Supponiamo di modificare il sottoprogramma INFIN dell'esem­pio 15.12 nel modo seguente:

SUBROUTINE INFIN (DATO, IND, LI, L2)LOGICAL INDCHARACTER DATO. (.), LI • l, L2. lN = LEN (DATO)IF (DATO(l: l ).EQ.Ll.AND.DATO (N:N).EQ.L2) THEN

IND= .TRUE.ELSE

IND = .FALSE.LI =DATO(l:l)L2 = DATO (N:N)

ENDIFRETURNEND

In questo caso il sottoprogramma può essere usato per determinare il primo e

l'ultimo carattere di qualsiasi stringa; infatti all'argomento muto DATO viene as­segnata, al momento della attivazione del sottoprogramma, la stessa lunghezzadell'argomento attuale corrispondente. Si osservi che in questa seconda versionedel sottoprogramma INFIN è necessario usare la funzione intrinseca LEN percalcolare la lunghezza di DATO.

Si osservi che un argomento muto di tipo carattere la CUI lunghezza sia stataspecificata con (.) può comparire come operando in una operazione di conca­tenazione soltanto in una frase di assegnazione.

Esempio 15.14. E' corretta la seguente sequenza di istruzioni, dove INFIN è

il sottoprogramma dell'esempio precedente:

SUBROUTINE CONCAT (X, Y, A, IN, FIN)CHARACTER. (.) X, Y, A. 3, IN • l, FIN. lLOGICAL INDY = X/lACALL INFIN (Y, IND, IN, FIN)

Page 151: Fortran

I

I294

no i punti xi = Xo + ih con O~ i ~ n. Si vuole scrivere un sottoprogramrna, dinome SGN, che permetta di individuare, se esiste, il più piccolo valore di j, con

0< j ~ n, tale che f(xj) f(x j_ 1) < O e, in caso affermativo. fornisca in uscita i va­

lori di j, Xj_ l' Xr Inoltre il sottoprogramma deve interrompersi se, per un valore

di i > O. si ha If(x) I~ € e in questo caso deve dare come risultati il valore j = - i

e il valore di Xi' Infine, se nessuna delle precedenti condizioni è verificata, il sot­

toprogramma deve fornire in uscita il valore j = n + I e i valori di Xo e xn '

Stabiliamo di utilizzare le variabili XO, H, N ed EPS come argomenti muti di

ingresso contenenti rispettivamente xo' h, n ed e, e la variabile JCS come argo­

mento di uscita che contiene il valore di j. Inoltre stabiliamo che l'argomento

muto XO contenga in uscita il valore di Xi se il sottoprogramma termina perché

If(x) I~ e, mentre usiamo gli argomenti XO e XN per memorizzare i valori di

xj_ 1 e Xj oppure Xo e xn negli altri due casi. Il sottoprogramma SGN, di tipo

SUBROUTINE, deve richiamare un altro sottoprogramma di nome FUNZ, con il

quale si calcola f(x) per un valore di x assegnato. Il sottoprogramma FUNZ può

essere di tipo FUNCTION e prevedere come unico argomento muto una variabile

reale che in ingresso contiene il valore di x; in uscita FUNZ fornisce il valore f(x).

II sottoprogramma SGN può essere quindi così formalizzato:

SUBROUTINE SGN (XO, XN, H, N, EPS, JCS)F = FUNZ(XO)SEGNO = SIGN (I., F)DOlO J=I,NXN = XO+ J. HF = FUNZ (XN)IF (ABS(F).LE.EPS) THEN

XO =XNJCS =-JRETURN

ELSE IF (SIGN(l., F).NE.SEGNO) THENXO =XN - HJCS = JRETURN

ELSEENDFI

IO CONTINUEJCS = JEND

La prima istruzione del sottoprogramma FUNZ richiamato da SGN deve essere

REAL FUNCfION FUNZ (X)

1295

e il suo corpo può descrivere qualunque funzione reale f(x) definita per x ;;;;. xo'D'altra parte, il sottoprogramma SGN non può essere usato se il sottoprogramma

che calcola f(x) ha un nome diverso da FUNZ. In particolare esso non può essere

utilizzato nella stessa unità di programma per esaminare il comportamento di

due o più funzioni distinte che sono ovviamente realizzate da sottoprogrammi

FUNCfION con nomi distinti. Perché ciò sia possibile, occorre modificare la pri­

ma istruzione di SGN inserendo il nome FUNZ nella lista degli argomenti muti;

in altri termini si deve usare un sottoprogramma, SGN I, il cui corpo è identico a

quello di SGN e la cui prima frase è

SUBROUTINE SGNI (XO. XN, H, N, EPS, JCS, FUNZ)

Durante l'esecuzione di SGN l ogni riferimento a FUNZ provoca l'attivazione del

sottoprogramma il cui nome è specificato nella lista degli argomenti attuali.

Così, se FCf, F e VALF sono i nomi di tre sottoprogrammi FUNCfION di tipo

reale e con un solo argomento di ingresso di tipo reale, è corretto il seguente uso

diSGNI:

EXTERNAL FCT,F,VALF

CALL SGNI (XO, XN, H, N, EPS, JCS, FCT)

CALL SGNI (XO, XN, H, N, EPS, JCS, F)

CALL SGNI (XO, XN, H, N, EPS, JCS, VALF)

L'istruzione EXTERNAL è indispensabile per poter usare FCf, F e VALF

come argomenti attuali corrispondenti a FUNZ.

Esempio 15.16. Sia F una funzione che associa ad ogni elemento x di IRn un vet­

tore y = F(x) di IRn . Assegnati due vettori u e v appartenenti ad IRn ed un intero

Q> O, sia xk ' con O~ k ~ Q, il vettore definito da:

Si vuoI scrivere un sottoprogramma che, supponendo noti u, v, ~, n ed F permet­

ta di determinare tra i vettori xk ' O~ k ~ Q, quel vettore xj tale che

Il F(xj)llz = min I] F(xk ) 112' O~ k ~ Q}

Il sottoprogramma richiesto, che chiameremo MF2, può essere scritto tenendo

presente il seguente algoritmo:

Page 152: Fortran

296

l. Dati: u, v, ~, n

2. Poni xj = v3. Calcola y = F(xj )

4. Calcola m = l y lil5. Ripeti per k = 1,2, ... ,~:

5. 1. poni (\ = k/ ~

5.2. poni xk = Q:kU + (I - Q:k) v

5.3. calcola y = F(xk

)

5.4. calcola mk = Il y Ib5.5. se mk ~ m allora: esegui 5.6

altrimenti: poni m = mkponi xj = xkesegui 5.6

5.6. continua il procedimento ripetitivo.

6. Risultati: m, xj

7. Stop

Si osservi che le istruzioni 4. e 5.4 di Questo algoritmo possono essere realiz­

zate tramite il sottoprogramma NORMA2 dell'esempio 15.9 la cui frase iniziale

è la seguente:

REAL FUNCfION NORMA2(X, N)

Inoltre, l'esecuzione delle istruzioni 3. e 5.3 prevede l'utilizzazione di un altro

sottoprogramma che identitichiamo con il nome FX e che, dato il vettore x, per­

metta di calcolare il vettore y = F(x). Il sottoprogramma FX deve essere di tipo

SUBROUTINE e deve prevedere due argomenti di tipo reale: quello di ingresso,

X, contenente il vettore x e quello di uscita, Y, contenente il vettore y = F(x).

Pertanto la frase iniziale di FX è

SUBROUTINE FX(X, Y)

mentre il corpo di FX è costituito da tutte le istruzioni che permettono di definire

i singoli elementi di Y.

Per definire la frase iniziale del sottoprogramma MF2 si noti che esso deve esse­

re una SUBROUTINE e che, per essere utilizzabile qualunque sia il valore di n.de­

ve prevedere il dimensionamento variabile dei vettori utilizzati. La lista degli ar­

gomenti muti di MF2 deve quindi comprendere i seguenti nomi di variabile. U,

V, L, N, XJ, M, XK, Y che rappresentano, rispettivamente, u, v, ~, n, Xj' m,

xk

' y. I primi quattro nomi indicano gli argomenti di ingresso; XJ ed M sono gli

argomenti di uscita; XK ed Y sono nomi di vettori che devono comparire nella

lista degli argomenti muti in quanto utilizzati con dimensionamento variabile.

La lista degli argomenti muti può inoltre comprendere il nome FX del sottopro-

297

gramma utilizzato per calcolare Ftx); questo permette l'utilizzazione di MF2

anche nel caso in cui la funzione Ft x) sia definita da un sottoprogramma la

cui frase iniziale ha la stessa forma indicata per FX ma il cui nome è diverso da

FX. Tenendo presente le osservazioni fatte, il sottoprogramma MF2 può essere

costituito dalle seguenti istruzioni:

SUBROUTINE MF2 (U, V, L, N, XJ, M, XK, Y, FX)REAL U(N), V(N), XJ(N), XK(N), Y(N)REAL M, NORMA2, MKOOlOl=I,N

lO XJ(I) = V(I)CALL FX(XJ, Y)M = NORMA2 (Y, N)RL=LDO 40 K = l, LALFAK = K/RLDO 20 I = l, N

20 XK(I) = ALFAK • U(I) + (I. - ALFAK) • V(I)CALL FX (XK, Y)MK = NORMA2 (Y, N)IF (MK.GE.M) GO TO 40M=MKDO 30 I = l,N

30 XJ(I) = XK(I)40 CONTINUE

RETURNEND

Supponendo che F(x) sia la funzione

essa può essere descritta mediante il seguente sottoprogramma:

SUBROUTINE FUNZ (X, Y)REAL X(3), Y(3)Y(I) = (X(2) •• 2 + 2.• EXP(- X(3»)/12.Y(2) = (I. - X(I) + SIN (X(3»)/6.Y(3) = (X(1) •• 2 + X(2) •• 2 + X(3) •• 2)/6.RETURNEND

Assegnati i vettori u = (I, l, I)T e v = (- l, - l, - 1)1 e fìssato P.e 15,ilsotto­

programma MF2 può essere utilizzato nel modo seguente:

Page 153: Fortran

~i

f.·i

,~

i

l

298

REAL Y(3), Y(3), XK(3), D(3), XJ(3)EXTERNAL FUNZREAD * D, YN=3L= 15CALL MF2 (D, Y, L, N, XJ, EMME, XK, Y, FDNZ)WRITE («, 1(0)(XJ(I), I = I, N)

100 FORMAT (IX, 'vETTORE DI MINIMA NORMA'/3 (IX, E13.6»WRITE (*,200) EMME

200 FO RMAT (I X, 'vALORE DELLA NORMA', 2X, E13.6)STOPEND

AI momento dell'attivazione di MF2 viene effettuata l'associazione tra gli

argomenti muti e quel1i attuali e, in particolare viene associato ad FX il nome del

sottoprogramma FUNZ. Il programma è pertanto costituito dal programma prin­

cipale e dai sottoprogrammi MF2, NORMA2 e FUNZ.

La frase INTRINSIC

Un nome simbolico in una lista di argomenti attuali viene interpretato come

nome specifico di una funzione intrinseca se nel1a stessa unità di programma esso

compare nella lista di una istruzione INTRINSIC. Questa frase dichiarativa, che

non esisteva in F66, ha la forma:

INTRINSIC lista

dove:

• INTRINSIC è la parola chiave che identifica la frase;

• lista è una lista di nomi specifici di funzioni intrinseche separati da virgole.

Si osservi che soltanto i nomi specifici delle funzioni intrinseche, e non i nomigenerici, possono essere usati come argomenti attuali e che, se in un'unità di pro­

gramma viene usato come argomento attuale il nome specifico di una funzione

intrinseca, questo nome deve comparire nella stessa unità di programma in una

frase INTRINSIC. Inoltre, non devono essere usati come argomenti attuali i nomi

di funzioni intrinseche che permettono conversioni di tipo (lNT, IFIX, IDINT,

FLOAT, SNGL, REAL, DBLE, CMPLX, ICHAR, CHAR), che stabiliscono l'or­

dinamento dei caratteri (LGE, LGT, LLE, LLT), che determinano il massimo o

il minimo di un insieme di valori numerici (MAX, MAXO, AMAX I, DMAX I,

AMAXO, MAX I, MIN, MINO, AMIN I, DMIN I, AMINO, MIN I).

Esempio 15.17. Fissati i valori di xo' n, h ed € si vuole studiare il comporta­

mento della funzione sin(x) nei punti Xi = Xo + ih, O :ç i :ç n, nel senso indi­

cato nell'esempio 15. I 5. Si può allora utilizzare il sottoprogramma SGN I facendo

corrispondere al1'argomento muto FUNZ il nome specifico SIN della funzione

T299

intrinseca che calcola sin(x) e che prevede un argomento di tipo reale. In questo

caso il nome SIN deve comparire in una istruzione INTRINSIC nel1a unità di pro­

gramma chiamante; in altri termini, questa deve contenere le due frasi seguenti:

INTRINSIC SIN

CALL SGNI (XO, XN, H, N. EPS, JCS, SIN)

In questo modo, durante l'esecuzione di SGN I, ogni riferimento a FUNZ è, di

fatto, un riferimento al1a funzione intrinseca SIN.

15.7. Asterischi come argomenti muti

L'asterisco può far parte del1a lista degli argomenti muti di un sottoprogramma

SUBROUTINE; ad esso deve corrispondere, come argomento attuale, uno specifi­

catare di ritorno alternativo che ha la forma:

* sdove• s è l'etichetta di una frase eseguibile appartenente al1a stessa unità di pro­

gramma in cui compare lo specificatore.

La denominazione «specificatore di ritorno alternativo» con la quale si indica

un argomento attuale del tipo * s è legata all'effetto di una particolare forma

della frase RETURN che può essere utilizzata al1'interno di un sottoprogramma

SUBROUTINE. Questa forma è la seguente:

RETURN

dove:

• RETURN è la parola chiave che identifica la frase;

• t è un espressione intera il cui valore è utilizzato per individuare !'istruzione

del programma chiamante che deve essere eseguita al1a fine del1'esecuzione del sot­

toprogramma. Più dettagliatamente, supponiamo che il sottoprogramma abbia n

argomenti muti del1a forma asterisco e che contenga l'istruzione

RETURN

AI momento dell'esecuzione di questa frase viene valutato il valore k dell'espres­

sione intera t. Se k < I oppure k > n la frase RETURN t ha lo stesso effetto

della frase RETURN. Se invece I :ç k :ç n, il valore k identifica il k-esimo asteri­

sco tra gli n presenti nella lista degli argomenti muti e il control1o dell'esecuzione

è rimandato all'istruzione della unità di programma chiamante la cui etichetta èassociata, mediante uno specificatore di ritorno alternativo, al k-esimo asterisco.

Page 154: Fortran

300

Esempio J5. J8. Indicate con LI ed L2 due lettere dell'alfabeto, si vuole scrivere

un sottoprogramma che permetta di stabilire se la stringa rappresentata dall'ar­

gomento muto VOCE inizia con LI e termina con L2, inizia con LI ma non ter­

mina con L2, termina con L2 ma non inizia con LI, non inizia con LI e non

termina con L2. In ogni caso, il sottoprogramma deve fornire il carattere iniziale e

finale di VOCE memorizzandoli in LI ed L2 rispettivamente. Tenendo conto che

il sottoprogramma deve selezionare uno fra quattro possibili casi, esso può preve­

dere fra gli argomenti muti tre asterischi ed essere realizzato nel modo seguente:

301

Se, durante l'esecuzione di RlTALT, viene eseguita l'istruzione RETURN,

allora l'esecuzione del programma principale prosegue con l'istruzione seguente

la CALL; essa prosegue invece con l'istruzione di etichetta IO, 20 o 30 rispetti­

vamente se in RlTALT viene eseguita l'istruzione RETURN l, RETURN 2 oRETURN 3.

La possibilità di usare i ritorni alternativi non esisteva in F66.

Esercizi

15.1 Scrivere un sottoprogramma mediante il quale, dati un vettore A di compo­

nenti al' ... , an e un vettore B di componenti bI' ..., bn

_ l' si costruisce

il termine dn di una successione {di' i = O, ... , n }definita da

do = l

dI = al

di = ai di_ l - br_ l di_ 2' per i = 2,3, ..., n

e si verifica se dn è maggiore di 1/3. Scrivere inoltre un programma che

utilizza questo sottoprogramma con i seguenti dati:

SUBROUTINE RIT ALT (VOCE, LI, L2, *, -. *)CHARACTER VOCE * (*), LI, L2N = LEN(VOCE)IF (VOCE(l: 1).EQ.L1.AND.VOCE(N:N).EQ.L2) RETURNIF (VOCE(l:l).EQ.L1) THEN

L2 = VOCE (N:N)RETURN l

ELSE IF (VOCE(N:N).EQ.L2) THENLI = VOCE(l:l)RETURN 2

ELSELI = VOCE (l : l)L2 =VOCE (N:N)

ENDIFRETURN 3END

Un programma principale che utilizza RITALT è il seguente:

n=6 A = (1,2, lO, - 5, 6, 8) B = (6, 7, 8, 9, lO).

Scrivere un nrogramrna che utilizza il sottoprogramma precedente con iseguenti dati:

m

Ci,j= L ai,k bk,j peri= l, ...,nej= l, ...,~k=l

Scrivere un sottoprogramma che calcoli il prodotto C = AB, dove A è una

matrice reale di n righe ed m colonne e B è una matrice di m righe ed ~ co­

lonne. Si ricorda che la matrice prodotto C ha n righe ed ~ colonne ed i

suoi elementi sono definiti da:

lO

20

30

CHARACTER * 7 NOME, IN * l, FIN * lREAD -. IN, FINPRINT *, 'CARATTERE INIZIALE DATO', INPRINT -. 'CARATTERE FINALE DATO', FINREAD *, NOMECALL RIT ALT (NOME, IN, FIN, * lO, *20, *30)PRINT -. 'NOME INIZIA CON:', IN,'E TERMINA CON:', FINSTOPPRINT -. 'L"ULTIMO CARATTERE DI NOME E":', FINSTOPPRINT -. 'IL PRIMO CARATTERE DI NOME E":', INSTOPPRiNT -. 'IL PRIMO CARATTERE DI NOME E":', INPRINT *, 'L"ULTIMO CARATTERE E":', FIN

STOPEND

15.2

(

- I

A= O

0.5

O

O

- l

3

-5

2.1

8.3 ) (O - 1.5)- ~.4 B = - ~.5 100

15.3 Scrivere un sottoprogramma mediante il quale, data una matrice reale A

di n righe ed m colonne, si determina il numero di variazioni di segno della

Page 155: Fortran

302 303

Scrivere infine un programma principale che, usando i due sottoprogrammi

precedenti, calcoli le variazioni di segno delle successioni {vi} associate alla

matrice MIO e alla matrice M6, La seconda matrice deve occupare le stessecelle di memoria della prima.

Scrivere un sottoprogramrna che, dato in ingresso un vettore intero di n

elementi, fornisca in uscita la posizione del massimo e del minimo elemen­

to. Scrivere inoltre un programma principale che utilizzi il sottoprogramma

per localizzare il massimo e il minimo elemento dei seguenti vettori:

tuno il caso in cui tutti gli elementi vk

' ' .. , vn siano minori o uguali di m.

l Jtilizzare il sottoprogramrna con i dati seguenti:

v=(0,14,17,18,20) k=2 m=15;

v = (- S, 2, 8, 1S, 30) k = 3 m = 31.

15.7 Siano a = (al' .. " an) e b = (bI' ..., bm) due vettori i cui elementi sononumeri interi distinti ordinati in senso crescente. Usando il sottoprogramma

scritto nell'esercizio precedente scrivere un altro sottoprogramrna che per­

metta di costruire un terzo vettore c = (Cl' . , ., cn+ m) tale che ogni suo

elemento sia un elemento di a o di b e, nel complesso, i suoi elementi siano

ordinati in senso crescente (per esempio, per a = (- 1,2) e b = (O, 5,7) si

ha c = (- 1, O, 2, S, 7)).

Scrivere un programma che utilizzi il sottoprogramma con i dati seguenti:

a = (15,20,100), b = (S, 6,35, SO, 5 I),

15.8 Dati due interi m ed n, sia ftx) la funzione definita nel modo seguente:

per i = 1, ... , n e j ~ i

per i = 1, .. "n e j > im(n) =

I,)

successione {vi' i = 1, ..., n}, dove vi è il massimo elemento della riga

i-esima di A. Scrivere inoltre un secondo sottoprogramma che, dato un

intero n > l, determini gli elementi m(n) di una matrice quadrata M diI,) n

ordine n definita da:

1jn + 1-1

15.4

(- l, O, 5,80) (5,8, - 4, l O) (40,50,60,70) (-3,-5,-8,-1) se x ~- 1

II programma deve usare un unico vettore di 16 componenti per memoriz­

zare i quattro vettori dati e due vettori di quattro elementi per memoriz­

zare le posizioni degli elementi massimi e degli elementi minimi rispettiva­

mente.

f(x) = m tg (- 7rx/4)

m . n 3- jf x) - - (x - 1)n m +

se-l<x~O

se x>O

15.5 Scrivere un sottoprogramma mediante il quale, assegnato il valore x, si cal­

cola il valore della funzione f(x) definita da:

dove j(x) e (x - l)~ sono date da:

se x ~ 1

se x < l.

Scrivere poi un programma principale che calcola e stampa la media arit­

metica dei valori f(l/3), f(5/2), t(O), f(4/3),

15.6 Sia v un vettore intero assegnato di componenti vI' ..., vn e siano k ,

1 ~ k ~ n, ed m due interi dati. Supponendo che le componenti di v siano

ordinate in senso crescente, scrivere un sottoprogramma che fornisca la

posizione e il valore del primo fra gli elementi vk ' ... , Vn il cui valore è

maggiore di m. Inoltre il sottoprogramma deve segnalare in modo oppor-

La funzione f(x) deve essere calcolata mediante un sottoprogramma di tipoFUNCfION supponendo che per il calcolo della funzione j(x) sia disponibi­

le una funzione esterna JX con le seguenti caratteristiche:

Scrivere un programma che provveda a leggere i valori di m ed n ed a me­

morizzare in un vettore e quindi stampare i valori assunti da f(x) nei punti

seguenti:

1 2 4- 3" O, 3" 3"' 1, 3

4 2- 3"' - 1, -'3'

Prima frase: REAL FUNCfION JX (X, N, A)

Scopo: calcolo del valore assunto nel punto x dal polinomio esponenzialen

j(x) = ~ a ck xk=O k

per O~ x < 1/2

per 1/2 ~ x < 1

per 1 ~ x ~ 3/2

altrimenti

sin (2x - l)

f(x) = sin (2x - l) + cos (2x - 1)sin (2x - l) + cos (2x - l) - tgx

O

I

"ì'

II,l'

(

Page 156: Fortran

305

304

15.9 Data l'equazione x = f(x) e posto Ntx) = f(f(x)) - 2 f(x) + x, sia

Fissato un valore Xo reale, sia {x k} la successione di valori reali definiti

da

Argomenti muti:X: variabile reale contenente in ingresso il valore di x;

N: variabile intera contenente in ingresso il valore di n;A: vettore intero di N + l elementi contenente in ingresso i coefficienti

<lo' al' ... , an ·

n=4, k=2, 1=(2,3), J=(1,3)

A = (~: ~~ ~: ~: )25 26 27 28

31 32 33 34In questo caso verranno modificati gli elementi delle prime 2 righe e 2 co­

lonne di A, che quindi avrà in uscita la forma seguente:

15.12 Assegnata una parola chiave costituita da Q lettere dell'alfabeto inglese,

si vuole codificare una frase data secondo il seguente sistema di codifica.

Alla parola chiave viene associato un vettore v = (VI' ..., v~) tale che v.è la posizione dell'i-esima lettera della parola chiave nell'alfabeto inglese.Così, per esempio, se la parola chiave è CHIAVE si ha v = (3, 8, 9, l,22,S).

Se il numero di caratteri della frase che si vuole codificare non è un multi­

plo di Q, si aggiungono in coda alla frase un certo numero di caratteri blank

in modo da ottenere una stringa, MESS, la cui lunghezza r sia multiplo di Q.

Così, continuando il nostro esempio, se la frase da codificare è

'UN '17 BEL 'I7PANORAMA' si ha MESS = 'UN '17 BEL 'I7PANORAMA'I7'17v'.

15.11 Scrivere un programma principale atto a:l) leggere i valori degli elementi di una matrice reale A di ordine lO e

deivettori 1=(iI,i2,i))e J=(jI,j2,j3);2) se gli elementi di I e J soddisfano le ipotesi del precedente esercizio

e hanno valori minori o uguale di 5 applicare il sottoprogramma COMP

alla sottomatrice di A costituita dagli elementi a.. con l· J. = l 5 eI,J ' , .. -, ,

stampare i risultati ottenuti; altrimenti interrompere l'esecuzione;3) applicare il sottoprogramma a tutta la matrice A precedentemente

trasformata usando i nuovi vettori I = (il + 5, i2 + 5, i3 + 5) e J =

= UI + 5, j2 + 5, j3 + 5) e stampare i risultati ottenuti.Verificare la correttezza del programma usando come dati iniziali la matri-

ce A di elementi a . = _1_ per i = l, ... , lO e j = l, ..., lO e i vettoril,l i + j

1= (1, 3,5), J = (2, 4,5).

se N(x) = O

se N(x) "1= O(f(x) - x)2

N(x)

x

xF(x) =

Xk + 1= F(xk )

che, sotto opportune ipotesi, converge alla soluzione x = s dell'equazione

data.Scrivere un algoritmo che, basandosi sul procedimento iterativo ora descrit-

to, permetta di realizzare quanto segue. Dati in ingresso i valori kmax > O,El > O, E

2~ O e E) ~ O con E2 ed E) non ambedue uguali a zero, determi­

nare se esiste un termine xj della successione {xk}, con j E;; kmax' tale che:

Ixj-F(xj_I)IE;;EI e \Xj-xj_IIE;;EIIXj_II+E2·

Se tale xj

esiste, esso è una stima della soluzione dell'equazione data; in

questo caso l'algoritmo deve fornire come risultati i valori di j, x. eJ

Ixj

- F(xj_ I) I· Se tale xj non esiste, l'algoritmo fornisce il risultato j == k

max+ l. Realizzare l'algoritmo ora descritto mediante un sottopro­

gramma che preveda fra gli argomenti muti anche il nome della funzione

esterna che descrive f(x).Utilizzare il sottoprogramma per calcolare una soluzione dell'equazionex = e- x con X

o= 0.5, scegliendo valori opportuni per kmax, El' E2, E).

15.10 E' assegnata una matrice reale A quadrata di ordine n, i cui elementi sono

indicati con ai,j' con i, j = l, ... , n. Sono inoltre dati due vettori interi

I = (il' ..., ik) e J = UI' ..., jk) con l :so;; k E;; n, per ognuno dei quali glielementi sono valori distinti compresi fra l ed n ordinati in senso crescente.

Si scriva un sottoprogramma di nome COMP che permetta di «compattare»

nella prime k righe e k colonne della matrice A gli elementi aip,jq con p,

q = l, ... , k. Utilizzare il sottoprogramma con i dati seguenti:

Page 157: Fortran

306

Ogni carattere di ogni sottostringa successiva di MESS di lunghezza Q,

indicata per semplicità come' Cl ... c~, viene sostituito nel modo seguente:

se Ci è un carattere blank, allora viene sostituito dalla vi-esima lettera del­

l'alfabeto; se invece Ci è la j-esima lettera dell'alfabeto, allora viene sostitui­to dalla lettera (j + vi)-esima se j + Vi ~ 26 o dalla lettera (j + Vi - 26)­

esima se j + Vi > 26 (ricordiamo che l'alfabeto inglese è composto da 26

lettere). Il risultato della codifica di MESS è una stringa, MESS l, composta

da k + l gruppi di Q lettere separati l'uno dall'altro da un carattere blank:il primo gruppo è la parola chiave; i successivi sono ottenuti codificando nel

modo descritto le sottostringhe di MESS. Così, nel nostro caso, la prima

sottostringa di MESS di lunghezza 6 è 'UNvBEL' e viene codificata come

'XVICAQ'; infatti:

U è sostituito da X perché VI = 3 e j = 21;

N è sostituito da V perché v2 = 8 e j = 14;

v è sostituito da I perché v3 = 9;

B è sostituito da C perché v4 = 1 e j = 2;

E è sostituito da A perché Vs = 22 e j = 5;

L è sostituito da Q perché v6 = 5 e j = 12.

La seconda e terza sottostringa di MESS, ossia ' v PANOR' e 'AMA v vv'

vengono sostituite rispettivamente da 'CMJOMW' e 'DUJAVE' .Così il risul­

tato è

MESS 1 = 'CHIAVE vXVICAQ vCMJOMW vDUJAVE'

Scrivere un sottoprogramma che, avendo come dati in ingresso una parola

chiave, KEY, e una stringa MESS, di lunghezza qualunque, controlli che la

lunghezza di MESS sia multipla di quella di KEY e, in caso affermativo,

esegua la codifica di MESS e fornisca come risultato la stringa MESS l.

Verificare la correttezza del sottoprogramma usando i dati utilizzati nel

corso di questo esercizio.

15.13 Scrivere un sottoprogramma ALF AB che permetta di ordinare alfabetica­mente gli N elementi di un vettore V di tìpo carattere. La lunghezza degli

elementi di V può essere qualunque.Scrivere un programma che utilizzi il sottoprogramma ALFAB per ordinare

gli elementi dei seguenti vettori:

VI = ('GIANNA', 'MARISA', 'ALVARO', 'MATTEO', 'FRANCO')

V2 = ('MATEMATICA', 'STORIAvvvv', 'GEOGRAFIAv', 'ITALIANOvv)

V3 = ('CANE', 'ALCE', 'LUPO', 'GUFO', 'OCA v', 'BUEv', 'BACO').

TI

16Uso flessibile della memoria

16.1. L'istruzione COMMON

La possibilità di strutturare un programma in varie unità, programma princi­

pale e sottoprogrammi, è una delle caratteristiche fondamentali del FORTRAN

ed è basata sul concetto di «località» delle variabili che figurano in ogni unità

di programma. D'altra parte le unità di programma devono scambiare informa­

zioni fra loro e una prima alternativa per soddisfare questa necessità è offerta dal

meccanismo di associazione fra argomenti muti e argomenti attuali. Tale mec­

canismo ha però un certo «costo» in termini di tempo d'esecuzione e occupazione

di memoria: infatti, al momento dell'attivazione di un sottoprogramma l'associa­

zione fra ogni argomento muto e il corrispondente argomento attuale viene realiz­

zata eseguendo delle operazioni che consentono la trasmissione degli indirizzi dei

parametri attuali dalla unità chiamante al sottoprogramma. In alcune situazioni

può essere vantaggioso evitare questi costi, per esempio quando si debbano tra­

smettere gli indirizzi di molti parametri molte volte durante l'esecuzione del

programma. A tale scopo si può usare il meccanismo di spartizione predichiaratadi una zona di memoria da parte di più unità di programma. espresso dall'istruzio­

ne dichiarativa COMMON. Usando tale istruzion-e sTp~ò infatti realizzare una se­

conda modalità di trasmissione di informazioni fra più unità di programma

che può essere usata insieme o in alternativa alla associazione fra argomenti muti

e argomenti attuali.

I blocchi COMMON

Un blocco COMMON è un insieme di unità di memoria numeriche consecutive

o un insieme di unità di memoria carattere consecutive, alle quali possono acce­

dere direttamente più unità di programma. Un blocco COMMON può essere indi­

viduato tramite un nome simbolico, detto nome o etichetta del blocco. nel qual

caso il blocco viene detto blocco COMMON etichettato. Il nome di un blocco

COMMON lo distingue dagli altri blocchi dichiarati nel programma e deve essere

diverso dai nomi delle unità che compongono il programma. Un blocco COMMON

Page 158: Fortran

308

può anche essere caratterizzato dall'assenza di un nome, nel qual caso il blocco

viene detto blocco COMMON non etichettato.I blocchi COMMON vengono definiti mediante l'istruzione dichiarativa

COMMON, la cui struttura è la seguente:

COMMON I nome} I lista}, Inome2/lista2' ... , Inomen/listandove:

• COMMON è la parola chiave che identifica la frase:

• nomei, con l E;;; i E;;; n, è il nome simbolico di un blocco COMMON oppure è

omesso. Ciascun nomei può essere usato, senza alcuna am biguità, come nome

di variabile nella stessa unità di programma;

• listai' per l E;;; i E;;; n, è una lista di nomi di variabile, nomi di variabile dimen­

sionata o dichiaratori di variabile dimensionata. In listai non possono coesistere

entità di tipo carattere con entità di tipo numerico oLo...&li;o; inoltre le variabili

dimensionate che figu;ano in lista. dev~no ave~~-di;~nsionamento-~~~tante:In~------- -1------ _

fine non possono far parte di listai argomenti muti della unità di programmain cui compare la frase COMMON. .-

Per effetto dell'istruzione COMMON alle entità i cui nomi compaiono in listai

vengono riservate unità di memoria consecutive; tali unità di memoria vengono

considerate parte del blocco COMMON individuato dal nome simbolico nomei,oppure di un blocco COMMON non etichettato se nomei è omesso.

Esempio 16.1. La frase

COMMON Il X(50), I NOMEI I Y, Z

dichiara due blocchi COMMON; il primo, non etichettato, comprende i 50 ele­

menti del vettore reale X, ovvero 50 unità di memoria numeriche consecutive;

il secondo, etichettato con il nome simbolico NOMEl, contiene le variabili Y e Z

alle quali il compilatore riserva due unità di memoria consecutive. Si osservi che

la frase data è equivalente alla coppia, di istruzioni

DIMENSION X(50)

COMMON Il X, INOMEI I Y, Z

Se in un'istruzione COMMON il primo nome simbohco, nome l , è omesso,

allora possono essere omesse anche le prime due sbarre; così la frase COMMON

dell'esempio precedente equivale alla frase

COMMON X(50), INOME l I Y, Z

Ancora, la virgola che segue ogni lista di nomi può essere omessa; così la frase pre­

cedente equivale a

309

COMMON X(50) INOME l I Y, Z

11 nome di un blocco può comparire più volte in una stessa frase COMMON () in

più frasi COMMON nella stessa unità di programma. In questo caso Il' liste asso­

ciate al nome del blocco vengono considerate, nell'ordine di apparizione. seg­

menti consecutivi di un'unica lista che determina la struttura del blocco. Le stesse

considerazioni valgono per il blocco COMMON non etichettato.

Esempio 16.2. Le sequenze di istruzioni

COMMON A, B I NOME2/ Y, WIl e, D.COMMON E, F I NOME2 I Z

e

COMMON A, B, e, D I NOME2 I Y, WCOMMON E, F INOME2 I Z

sono fra loro equivalenti, ed ambedue hanno lo stesso effetto dell'unica frase

COMMON A, B, C, D, E, F I NOME2 / Y. W. Z

La lunghezza di un blocco COMMON è data dal numero di unità di memoria

che lo compongono; in generale la lunghezza di un blocco è uguale al numero di

unità di memoria consecutive riservate agli elementi della lista associata al suo

nome (cfr. § 16.4).

Esempio 16.3. Con le frasi di specificazione seguenti

CHARAeTER.8 CAR (lO)REAL REX, REYDOUBLE PRECISION DP(15)COMMON IBLOC1/REX,DP. IBLOC2/REY, IBLOC31CAR

vengono definiti tre blocchi COMMON. Ricordando che a un dato in doppia pre­

cisione vengono riservate due unità di memoria numeriche consecutive, si deduce

che il primo blocco, BLOCI. è costituito da 31 unità di memoria numeriche; il

secondo, BLOC2, è costituito da l unità di memoria numerica e il terzo, BLOC3,

da 80 unità di memoria carattere. Pertanto i tre blocchi hanno lunghezza rispet­

tivamente 31, l ed 80.

16.2. Utilizzazione dei blocchi COMMON

Blocchi COMMON etichettati

In più unità di programma si possono definire blocchi COMMON etichettati

~IIII

~"

:11

Page 159: Fortran

blocco COMMON di nome UNO

X(\) Y(\)

X(2) Y(2)

X(3) Y(3)

X(4) Y(4)

X(S) ZO,I )

X(6) Z(2,I)

X(7) Z(1,2)

X(8) Z(2,2)

I

ii(

"

310

con lo stesso nome. In questo caso i blocchi devono essere costituiti con lo stesso

tipo di unità di memoria (carattere o numerico) e devono avere la stessa lunghez­

za. Durante l'esecuzione del programma tali blocchi occupano la medesima zona

di memoria. Così, se in più unità di programma si definiscono blocchi COMMON

_con lo ~tesso nome, SI definisce di fatto un gruppo di celle di memoria consecu­

tive i_contenuti delle quali sono direttamente utilizzabili da queste unità. Le

liste associate al nome del blocco nelle diverse unità di programma specificano

i nomi locali che ogni unità utilizza per identificare le celle del blocco.

Esempio 16.4. Un programma comprende il programma principale di nome

MAIN e i due sottoprogramrni SUBI e SUB2 seguenti:

PROGRAM MAINCOMMON /UNO/X(8), /DUE/N, M

END

SUBROUTINE SUBICOMMON /UNO/Y(4), Z(2, 2)

END

MAIN SUBI MAIN SUB

~~

blocco COMMON di nome DUE

311

SUBROUTINE SUB2COMMON /DUE/I, J

END

Nel programma vengono definiti due blocchi COMMON, di nomi UNO e DUE,

di lunghezza B e 2 rispettivamente. II primo blocco è definito nel programma pnn­

cipale e nel sottoprogramma SUB l e le celle del blocco sono identificate con i

nomi Xt l ), X(2), ... , X(B) e Y( I), ... , Y(4), Z(l, I), .. " Z(2, 2) rispettivamente

nelle due unità dr programma. Al secondo blocco invece hanno accesso il program­

ma principale e il sottoprogramma SUB2 che ne identificano le celle con i nomi

N, M e I, J rispettivamente. Così, i valori attribuiti nel programma principale

agli elementi del vettore X sono direttamente utilizzabili dal sottoprogramma

SUB I come valori degli elementi di Y e Z, e viceversa. Analogamente i valori asse­

gnati ad N e M nel programma principale vengono direttamente trasmessi al sotto­

programma SUB2 che vi fa riferimento con i nomi I e J, e viceversa. In fig. 16.1

sono schematicamente rappresentati i due blocchi COMMON: ogni rettangolo

rappresenta una cella di memoria e i nomi all'interno del rettangolo sono i nomi

che identificano la cella nelle diverse unità di programma.

Figura 16.1. Rappresentazione dei blocchi COMMON definiti nell'esempio 16.4.

Il blocco COMMON non etichettato

1 blocchi COMMON /IO/I etichettati definiti iII più unità di programma pOSSOIlO

avere lunghezze diverse; iII ogni caso la loro prima unità di memoria è la stessa e

quindi essi definiscono zone di memoria che si sovrappongono del tutto o in

parte. In altri termini in un programma si può definire una zona della memoria. il

blocco COMMON non etichettato. costituita da un numero di unità di memoria

pari alla massima lunghezza dei COMMON non etichettati dichiarati nelle singole

(

. unità di programma; ognuna di queste unità può direttamente utilizzare i conte­

nuti delle prime Q unità di memoria del blocco se Q è la lunghezza del blocco

COMMON non etichettato in essa dichiarato.

Esempio 16.5. In fig. 16.2 sono rappresentate quattro unità di uno stesso pro­

gramma. ognuna delle quali contiene la specificazione di un blocco COMMON

non etichettato. Nei sottoprograrnmi NO\fE I e ~O\fE3 il blocco ha 11111~hena

6, mentre in NOME2 e NOME4 ha lunghezza 2 e 4 rispettivamente. Pertanto ri­

sulta definito nel programma un blocco COMMON non etichettato di lunghezza

6; le unità NOMEI e NOME3 hanno accesso a tutte le celle del blocco. mentre

NOME2 può accedere soltanto alle prime due e NOME4 soltanto alle prime

Page 160: Fortran

312 313

NOMEI NOME2 NOME3 NOME4

SUBROUTINE NOME lREAL A, B, CCOMMON A, B, C(4)

(

COMMON sono uno strumento molto meno flessibile delle liste di argomenti;!così, per esempio, in essi non devono figurare variabili dimensionate con di­

mensionamento variabile e ciò può limitare le possibilità di utilizzo di un sot­toprogramma.

Esempio 16.6. Consideriamo il programma di fig. 16.3, costituito dal sottopro­

gramma ORD che permette di ordinare in senso crescente i contenuti degli N ele­menti di un vettore X e dal programma principale MAIN che lo utilizza. Le due

unità di programma comunicano attraverso la lista degli argomenti. Possiamomodificare le unità ORD e MAIN in modo da ottenere un programma principaleMAINI e un sottoprogramma ORDI che sono analoghi ai precedenti ma utiliz­zano come canale di comunicazione un blocco COMMON non etichettato (cfr.fig. 16.4). Si può notare che la frase

REAL X(N)

del sottoprogramma ORD viene sostituita dalla frase

REA L X(SO)

nel sottoprograrnma ORD 1, in quanto il vettore X fa parte di un blocco COMMON

A A M(l) C(l)

B B M(2) C(2)

C(l) M(3) C(3)

C(2) M(4) C(4)

C(3) M(S)

C(4) M(6)END

SUBROUTINE NOME4REAL CCOMMON C(4)

END

SUBROUTINE NOME3INTEGER MCOMMON M(6)

END

SUBROUTINE NOME2REAL A, BCOMMON A, B

END

Figun 16.2. Sottoprogrammi e blocco COMMON deU'esempio 16.5.

quattro. Si noti che nel sottoprogramrna NOME3 le celle sono individuate con

nomi di tipo intero, mentre nelle altre unità si utilizzano nomi di tipo reale.

/

1 Osservazione. Si not.i che l'associazione che viene stabilita fra le variabi!i !,resen~~

... in un blocco ~()~~ON che figura in più unità di programma è indi~~nte dalI tipo di queste variabili: è quindi estremamente importante che il programmatore

ponga moltaattenzione ai possibili effetti non desiderati derivanti dal disaccordo

in tipo fra variabili che spartiscono le medesime unità di memoria.

l blocchi COMMON possono essere utilizzati con un duplice scopo. Attraverso

la definizione di zone di memoria utilizzabili da più unità di programma si può

ridurre talvolta la quantità di memoria necessaria alla esecuzione di un program­

ma. D'altra parte i blocchi COMMON costituiscono veri e propri canali di comu­

nicazione fra unità di programma e possono essere usati per scam bio di informa­zioni. Rispetto all'associazione fra parametri muti e parametri attuali, l'uso dei

blocchi COMMON presenta il vantaggio di una maggior velocità di esecuzione;infatti in questo caso non si eseguono operazioni per realizzare la trasmissionedelle informazioni in quanto i blocchi vengono definiti dal compilatore e dallinker nelle fasi che precedono l'esecuzione. Osserviamo però che i blocchi

j

PROGRAM MAINREAL X(SO)READ -. N, (X(I), I = l, N)WRITE(*, 3)(X(I), I = l, N)

3 FORMAT(lX, 'vETTORE DA RIORDINARE' / S(lX, EI3.6)CALL ORO (X, N)WRlTE(*,5) (X(I), I = l, N)FORMAT(l X, 'VETTORE RIORDINATO' / S(lX, EI3.6»STOPEND

SUBROUTINE ORD(X, N)REAL X(N)

C RIORDINAMENTO IN SENSO CRESCENTEC DEGLI ELEMENTI DEL VETTORE X

0010 1=I,N-IXMIN = X(I)DO 20 J = I + l, NIF (X MIN.GT.x(J)) XMIN = X(J)

20 CONTINUEX(I) = XMIN

IO CONTINUERETURNEND

Figura 16.3. Scambio di informazioni fra unità di programma attraverso la lista degli argomenti(esempio 16.6)

Page 161: Fortran

314

PROGRAM MAINIREAL X(50)COMMON N, X

CALL ORDI

END

SUBROUTINE ORDIREAL X(50)COMMON N,X

END

Figura 16.4. Scambio di informazioni fra unità di programmaattraverso un blocco COMMON (esempio 16.6).

e non può quindi avere dimensionamento variabile. Si osservi che questa forma

di dimensionamento potrebbe essere mantenuta lasciando X fra gli argomenti

muti di ORD e mettendo N in un blocco COMMON.

Osserviamo che in alcune situazioni l'uso dei blocchi COMMON può rivelarsi

molto vantaggioso se non si vogliono modificare sottoprogrammi già scritti.

Esempio 16.7. Consideriamo la seguente funzione della variabile x

(I + a)f(x) = x2 - 2ax + --- - 2a

log x

315

PROGRAM MALFA

COMMON /MAINFX/ALFA

PARAMETER (A = IO., B = 100.)EXTERNAL FXALFA

REA D e , N, EPS

H = (B - A)/N

ALFA = O.

DO 20 1 = l, IO

ALFA = ALFA + 0.1

XO= ACALL SGNI (XO, XN, H, N, EPS, JCS, FXALFA)

WRITE (., 3), ALFA, JCS

3 FORMAT(/ IX, 'ALFA =', F3.I, 5X. 'JCS =',15)

20 CONTINUE

STOP

END

FUNCTION FXALFA(X)

COMMON /MAINFX/ALFAFXALFA = X • X - 2.• ALFA. X + (1. + ALFA)/LOG(X) - 2.• ALFA

RETURN

END

Osserviamo che il programma è composto dal programma principale MALFA

e dai sottoprogrammi SGN l ed FXALFA. L'uso del blocco COMMON ci con­

sente di «scavalcare» SGN l e passare l'informazione relativa ad ALFA diret­

tamente da MALFA a FXALFA. In fig. 16.5 rappresentiamo schematicamente

il modo in cui la memoria viene utilizzata e il modo in cui avviene la trasmissione

di informazioni fra le varie parti della memoria.

Figura 16.5. Utilizzazione della memoria e scambio di infonnazioni fra unità di programma

(cfr. es. 16.7).

dove a è un parametro reale che può assumere i valori 0.1, 0.2, ... ,0.9, l. Fissatol'intervallo di estremi a = l O, e b = 100., e assegnati i valori n > O e € > O, si

vuole utilizzare il sottoprogramma SGN l dell'esempio 15.15 per studiare il com­

portamento di f(x), per ogni valore di a, sui punti xi = a + ih, con i = O, ..., n e

h = (b - alIno

La SUBROUTINE SGN l richiede la definizione di un sottoprogramma di tipo

FUNCTION, con un unico argomento muto che rappresenta la variabile indi­

pendente x, Nel nostro caso quindi, non potendo utilizzare la lista degli argo­

menti per trasmettere alla funzione il valore di a, dovremmo definire per ogni

valore di a un sottoprogramma FUNCTION distinto. Si può evitare tale dispen­

dioso modo di procedere ricorrendo alla definizione di un blocco COMMON

opportuno. Quanto detto è esemplificato nel seguente programma principale e

nel sottoprogramma FXALFA.

Memoria locale Unità di programma

MAIN

Blocchi COMMON

accesso di una unità

- di programma alla

sua memoria locale

scambio di informazioni

~-----. tramite la lista di

argomenti muti e attuali

accesso al blocco

COMMON

Page 162: Fortran

317

Figura 16.6. Effetto dell'istruzione EQUIVALENCE dell'esempio 16.8.

precedenti figure, ogni rettangolo rappresenta una unità di memoria, e i nomi alsuo interno sono i nomi usati per identificare questa unità; nel caso della variabilecomplessa OMEGA, il nome identifica due unità di memoria numeriche.

Si osservi che l'eventuale spartizione di una o più unità di memoria da parte dientità di tipo diverso non implica alcuna operazione di conversione. Osserviamo

inoltre che, evidentemente, un'istruzione EQUIVALENCE non deve implicaresovrapposizioni di unità di memoria che devono essere distinte o la «separazione»

di unità di memoria che devono essere consecutive. Pertanto sono sbagliate dichia­razioni del tipo

REL(I)

REL(3)

REL(2)

REL(4)I----OMEGA-

ALFA (1 : 1) CAR (1)

ALFA (2: 2) CAR (2)

ALFA (3 : 3) CAR (3)

ALFA (4: 4) CAR (4)

ALFA (5: 5) CAR (5)

ALFA (6: 6)

mente 6 e 5 unità di memoria carattere, hanno in comune le prime 5 di queste;pertanto il nome CAR (1). con 1 :E;;; I :E;;; S, identifica la stessa unità di memo­

ria identificata dal nome ALFA (I : I). Ancora, la variabile di tipo complessoOMEGA occupa due unità di memoria numeriche consecutive, mentre REL(3)è il terzo elemento del vettore reale REL che ha ampiezza 4; pertanto le unitàdi memoria occupate da OMEGA coincidono con quelle occupate da REL(3)e REL(4). Infine, i tre nomi I, J e K identificano la stessa cella di memoria. Infig. 16.6 si rappresenta in modo schematico l'effetto ora descritto. Come nelle

316

dove:

• EQUIVALENCE è la parola chiave che identifica la frase;

• per ogni i, l <; i .;; n, listai è una lista composta da almeno due nomi, separatida virgole; listai può contenere nomi di variabile, nomi di variabile dimensionata,nomi di elementi di variabile dimensionata con indici costituiti da espressioni

costanti intere, e nomi di sottostringhe. L'occorrenza in listai di un nore di va­riabile dimensionata è equivalente all'occorrenza del suo primo elemento. Nonpossono coesistere in listai entità di tipo carattere con entità di tipo numericoo logico; inoltre non possono figurarvi argomenti muti della unità di programmain cui la frase EQUIV ALENCE compare.

Per effetto della dichiarazione EQUIVALENCE tutte le entità che compaionoin ciascuna listai' con l .-; i <;; n, hanno in comune la prima unità di memoria.Da ciò può seguire che due o più entità in una stessa lista spartiscano, oltre allaprima, altre unità di memoria.

16.3. L'istruzione EQUIVALENCE

L'idea della spartizione di una cella di memoria da parte di più variabili espressadalla frase COMMON si trova anche nella frase. dichiarativa EQUIVALENCE.La differenza fondamentale rispetto alla frase COMMON risiede nel fatto checon la frase EQUIVALE:~ç~ viene dichiarata la spartizione di una zona dellamemoria da parte di più variabtl; nella medesima unità di tuozmmma. Esi­

stono varie circostanze nelle quali può risultare utile sfruttare le possibilità of­ferte dalla dichiarazione EQUIVALENCE; essa infatti consente di riferirsi allamedesima quantità con nomi diversi ed è quindi utilizzabile, ad esempio, quandosi vuole risparmiare memoria in presenza di grandi quantità di dati. In quest'ul­

timo caso, quando ad esempio una variabile dimensionata sia già stata elaborata

e la sua presenza in memoria non sia ulteriormente necessaria, un'altra variabiledimensionata, il cui nome ci interessi mantenere distinto da quello della prima,

può occupare in tutto o in parte lo spazio di memoria occupato dalla prima.La forma della frase EQUIVALENCE è la seguente:

EQUIVALENCE (listai)' (list~)•...• (listan

)

Esempio 16.8. Consideriamo le seguenti istruzioni:

CHARACTER ALFA. 6, CAR(5). IREAL REL(4)COMPLEX OMEGAEQUIVALENCE (ALFA, CAR), (OMEGA, REL(3», (I, J, K)

L'effetto di queste frasi è il seguente: ALFA e CAR, che occupano rispettiva-

DIMENSION A(2)EQUIVALENCE (A(l), B), (A(2), B)

oppure

REAL A(2)COMPLEX C(2)EQUIVALENCE(A(I), C(I »,(A(2), C(2»

Page 163: Fortran

':i. [I

:1

I,I

318

Anche alla luce delle precedenti osservazioni, occorre molta attenzione nell'u­tilizzare la frase EQUIV ALENCE soprattutto in relazione a variabili dimensionate.

Esempio 16.9. Si considerino le seguenti frasi di specificazione

REAL A(6), B(2, 3), C(6)EQUIVALENCE (A, B), (B(I, 2), C(3»

Il significato di questa frase EQUIVALENCE può essere il seguente: il primo ele­mento del vettore A ed il primo elemento della matrice B occupano la medesima

cella di memoria ed il primo elemento della seconda colonna della matrice B

occupa la stessa cella del terzo elemento del vettore C. Esaminiamo però gli effetti

implicitamente derivanti dalla frase EQUlVALENCE, dovuti al fatto che A, B e

C sono variabili dimensionate ed occupano ciascuna 6 unità di memoria conse­

cutive. L'effetto complessivo nel nostro caso è quello descritto in fig. 16.7, dove

si nota in particolare che dalla sovrapposizione fra B( l, 2) e C(3) segue la sovrap­

posizione totale fra la matrice B e il vettore C. Pertanto le frasi considerate sonoequivalenti alle frasi

REAL A(6), B(2, 3), C(6)EQUIVALENCE (A, B, C)

Esempio 16.10. Le dichiarazioni seguenti

REAL A(2, 2), B(2, 2)EQUIVALENCE (A(I, 2), BO, I»

producono l'effetto schematizzato in fig. 16.8, ovvero la sovrapposizione fra laseconda colonna della matrice A e la prima colonna della matrice B.

1319

16.4. Interazione fra istruzioni COMMON ed EQUIVALENCE

E' possibile che una variabile, dimensionata o non dimensionata, figuri in una

frase COMMON e in una frase EQUIV ALENCE nella stessa unità di programma,

purché l'effetto congiunto delle due frasi non dia luogo alle seguenti situazioni

non consentite. Innanzitutto un'istruzione EQUIVALENCE non deve creare so­vrapposizioni fra blocchi COMMON distinti; per esempio è sbagliata la compre­

senza nella stessa unità di programma delle seguenti frasi

COMMON!COMI! A(lOO), B(lOO)COMMON!COM2! X, YEQUIVALENCE (B(lOO), X)

In questo caso, infatti, l'ultima cella di memoria del blocco di nome COM I

si sovrapporrebbe alla prima cella del blocco di nome COM2. Si osservi inoltreche dall'interazione tra una frase COMMON e una frase EQUlVALENCE può

seguire un allungamento di un blocco COMMON. Per spiegare in cosa consistequesto fenomeno conviene ricorrere ad un semplice esempio.

Esempio 16.11. Consideriamo le seguenti istruzioni

REAL D(3)COMMON IX! A, B, CEQUIV ALENCE (C, D(I»

Per effetto della frase EQUIV ALENCE la terza unità di memoria del blocco

COMMON coincide con l'unità di memoria riservata al primo elemento del vet­

tore reale D. In questo caso anche i restanti due elementi di D vengono consi­derati parte del blocco COMMON (cfr. fig. 16.9.a); pertanto le istruzioni datesono equivalenti alle seguenti

A(I) B(l,I) C(I)

A(2) B(2,1) C(2)

A(3) B(I,2) C(3)

A(4) B(2,2) C(4)

A(5) B(I,3) C(5)

A(6) B(2,3) C(6)

Figura 16.7. Effetto della fraseEQUlVALENCE nell'esempio 16.9.

A(l,I)

A(2,1)

A(l,2) B(I,I)

A(2,2) B(2,1)

B(I,2)

B(2,2)

Figura 16.8. Effetto della fraseEQUIVALENCE nell'esempio 16.10.

REAL D(3)COMMON IX! A, B, OEQUIVALENCE (C, 0(1»

e il blocco COMMON ha lunghezza 5 anziché lunghezza 3 come risulterebbedalla sola frase

COMMON IXI A, B, C

Ancora. la sequenza di istruzioni

REAL 0(3)COMMON IX! A, B, CEQUIVALENCE (B, O (I»

Page 164: Fortran

equivale alla sequenza

e in questo caso il blocco COMMON ha lunghezza 4 (cfr. hg. 16.9.b).

REAL 0(3)COMMON /X/ A, DEQUIVALENCE (8, D(1», (C, 0(2» i

l

III

A D(3)

B

C

0(1)

D(2)

Figura 16.10. Allungamento non consentito di un blocco COMMON.

321

La frase DATA consente di predefinire, ossia definire prima dell'esecuzione,

in fase di compilazione, il valore di una variabile, di una variabile dimensionata,

di un elemento di una variabile dimensionata, di una sottostringa. I valori asse­

gnati con una frase DATA restano inalterati per la durata dell'esecuzione dell'inte­

ro programma, a meno che non vengano esplicitamente modificati nell'unità di

programma in cui la frase DATA compare.La frase DATA è una frase non eseguibile che può apparire in qualsiasi punto

di una unità di programma dopo le frasi di specificazione e prima della END.

Tale frase ha la forma seguente:

16.5. La frase DATA

b)

A

8 D(1)

C 0(2)

0(3)

a)

Figura 16.9. Allungamenti del blocco COMMON nell'esempio 16.11.

A

8

C 0(1)

D(2)

0(3)

320

L'allungamento di un blocco COMMON etichettato per effetto di frasi

EQUIVALENCE in una unità di programma è consentito purchè sia rispettata la

regola secondo la quale i blocchi COMMON con lo stesso nome definiti in unità

di programma diverse devono avere la stessa lunghezza. In ogni caso, anche per il

blocco COMMON non etichettato, vale la seguente restrizione: un blocco COMMON

può essere allungato soltanto «a destra», ovvero con l'aggiunta di unità di memo­

ria successive all'ultima. Pertanto è sbagliata la sequenza di istruzioni

REAL D(3)COMMON /X/ A, B, CEQUIVALENCE (A, D(3»

secondo la quale l'elemento D(3) si sovrappone alla prima unità di memoria del

blocco COMMON; ciò provocherebbe un allungamento non consentito «a sini­

stra», come illustrato in fig. 16.10.

dove:• DATA è la parola chiave che identifica la frase;• le virgole che separano ogni coppia nlistaJvlistaJ dalla successiva, possono

essere omesse;• ciascuna nlista

i, per I ~ i ~ n, è una lista di nomi di variabile; nomi di variabile

dimensionata, nomi di elementi di variabile dimensionata, nomi di sottostringa

e liste con DO-implicito. Le espressioni indice nei nomi di elementi di variabile

dimensionata e le espressioni di sottostringa nei nomi di sottostringa devono

essere espressioni costanti intere;• ciascuna vlista

i, per I ~ i ~ n, è una lista di costanti, nomi simbolici di costante,

o simboli della forma r * c, dove r è (un nome simbolico di) una costante intera

non nulla senza segno e c è una costante o un nome simbolico di costante. La

presenza di un simbolo r * c è equivalente alla presenza di r costanti successive

uguali a c separate da virgole. Tenendo presente che ogni nome di variabile dimen­sionata in nlista

iè equivalente alla lista dei nomi dei suoi elementi nell'ordine in

,:1

1

Page 165: Fortran

322

cui compaiono in memoria, il numero di valori costanti espressi in nlista i deve

essere uguale al numero di componenti di nlista.. Infatti viene stabilita una corri­

spondenza uno-a-uno fra gli elementi di nlista i e quelli' di vlista j e ogni elemento

di nlista. viene predefinito con il corrispondente valore in vlista j . Di questa prede-I . .

finizione si tiene conto attraverso la tavola dei sim boli (cfr. cap. 2) che in COrrI-

spondenza di ogni entità presente in una frase DAT A riporta. oltre all'indirizzo

della sua prima unità di memoria, anche il suo valore iniziale. Da quanto detto

segue che ad ogni elemento di tipo logico o carattere in nlista i deve corrispondere

un valore dello stesso tipo in vlista.. Si osservi inoltre che la predefinizione di un

elemento di tipo carattere avviene secondo le regole dell'assegnazione carattere

e quella di un elemento di tipo numerico può implicare un'operazione di conver­

sione secondo le specifiche della frase di assegnazione aritmetica.

Si osservi che la frase DATA non può essere usata per predefinire entità che

facciano parte di un blocco COMMON non etichettato o della lista di argomenti

muti nella stessa unità di programma. Le entità che fanno parte di un blocco

COMMON etichettato possono invece essere predefinite soltanto nel corpo di un

sottoprogramma BLOCK DATA, come vedremo nel paragrafo successivo.

Esempio J6. J2. Sono corrette le seguenti istruzioni:

DATA UNO, DUE, TRE 11.,2.,3./, I, J, K I 3 * O

DATA TRE. CINQUE I 3,5

DIMENSION V(lO, IO), U(l5)DATA V I 100 * 0./, U I IO * O., 1.,2.,3.,4.,5./

CHARACTER * 2 MAT (3, 3), VARDATA MAT(I, l), MAT(2, 2), MAT(3, 3), VAR 14 * 'UN'

Sono invece sbagliate le seguenti:

DATA A,B 13*0.51

DOUBLE PRECISION D(5,5)DATA D I 20*0.5D-21

CHARACTER * 4 NOMEDATA NOME,X I 3.2, 'ANNA'I

Infatti nei primi due casi nlista i e vlista i non contengono lo stesso numero di

elementi, mentre nel terzo la variabile NOME, di tipo carattere, viene predefinita

con un valore reale e la variabile reale X con un valore di tipo carattere.

I\

I

323

Esempio J6.13. Consideriamo le seguenti istruzioni:

REAL B(l5,I5)CHARACTER * 6 NOME(41DATA B 1225 * 0./, NOMEI 'GUIDO', 'BRUNO', 'GIULIO', 'LAPO'/

A tutti gli elementi della matrice B viene assegnato in fase di compilazione il

valore zero, mentre gli elementi del vettore carattere NOME conteranno all'inizio

dell'esecuzione le stringhe 'GUIDOv', 'BRUNOv', 'GIULIO, ' LAPOvV. Infatti

i contenuti di B e NOME risultano definiti come se venissero eseguite le frasi diassegnazione seguenti:

DOlO 1==1,15DO IO J == l, l 5

IO B(I, J) == O.NOME(I) == 'GUIDO'NOME(2) == 'BRUNO'NOME(3) == 'GIULIO'NOME(4) == 'LAPO'

Osserviamo che i valori preassegnati agli elementi di B e di NOME possono es­

sere modificati durante l'esecuzione del programma.

Come l'esempio precedente suggerisce, le frasi DATA possono essere vantag­

giosamente utilizzate per predefinire variabili dimensionate di grosse dimensioni;

in questi casi infatti la predefinizione in fase di compilazione permette un notevo­

le risparmio di tempo rispetto, per esempio, all'esecuzione di un gran numero di

frasi di assegnazione. Talvolta la frase DATA può essere usata con uno scopo ana­

logo a quello dell'istruzione PARAMETER, ovvero per poter usare nel corpo di

una unità di programma un nome simbolico per riferirsi ad una quantità che non

cambia durante l'esecuzione del programma. Così. per esempio, le due frasi

DATA I EPS I LE -0.5PARAMETER (EPS == LE - 0.5)

consentono am bedue di utilizzare il nome sim bolico EPS in luogo della costante

I.E - 0.5. D'altra parte le due frasi non sono equivalenti; infatti nel primo caso

EPS è un nome di variabile e il suo valore può essere modificato successivamente

durante l'esecuzione. mentre nel secondo caso EPS è un nome di costante.

Liste con DO-implicito nella frase DAT A

In una frase DATA possono figurare liste con DO-implicito con lo stesso signi­

ficato ad esse attribuito nelle liste di I/O. Lo standard F77 impone però alcune re-

Page 166: Fortran

------.-...._------ .- .._-- -----

324

strizioni alle liste con DO-implicito presenti nelle frasi DATA; esse infatti devonoavere la forma seguente:

dove:• Y è la lista del DO-implicito in cui possono figurare soltanto nomi di elementi

di variabile dimensionata, e, eventualmente, altre liste con DO-implicito;

• i è la variabile del DO-implicito e deve essere una variabile di tipo intero;

• mI' m2, m3 hanno lo stesso significato attribuito ai simboli vI' v2, v3 nelle listecon DO-implicito nelle frasi di I/O; mI' m2 ed m3 devono essere espressioni costan­

ti intere se la lista con DO-implicito non è contenuta in un'altra lista con DO-im­

plicito; altrimenti mI' m2 ed m3 possono essere espressioni intere che contengonocostanti, nomi simbolici di costanti e le variabili (ovviamente diverse da i) delle

liste con DO-implicito più esterne. In ogni caso i valori di mI' m2 , m3 devono

essere tali da implicare almeno una ripetizione della lista.

Esempio 16.14. Le frasi

PARAMETER (N = 5)DATA (V(I), l = l, N) /5.0./

sono corrette. In particolare è corretto l'uso del nome simbolico N nella lista con

DO-implicito in quanto N è un nome di costante. E' invece sbagliata la sequenza

DATA N / 5/DATA (V(I), l = l, N) /5.0./

perché in questo caso N è un nome di variabile e non è la variabile di una lista

con DO-implicito esterna a (V(I), I = l, N).

Esempio 16.15. La frase

DATA «X(K, J), J = K, 5), K = 1,5) /15 * 0./

è corretta e definisce come zero i quindici elementi della matrice X che compon­

gono la lista con DO-implicito. Lo stesso effetto, in fase di esecuzione, si otterreb

be con le frasi:

00 15 K = 1,500 15 J = K,5

15 X(K.J)=O.

Si osservi che la definizione della variabile di una lista con DO-implicito nella

frase DATA non implica alcuna predefinizione per una eventuale variabile con

325

il medesimo nome che figuri nella medesima unità di programma.

Osserviamo infine che la frase DATA era prevista anche in F66, ma con alcune

differenze rispetto alla forma e alle modalità di utilizzo qui descritte (cfr. appen­dice A2).

16.6. Sottoprogrammi BLOCK DATA

Se si vuole predefinire con una frase DATA un'entità che fa parte di un bloccoCOMMON etichettato, si deve utilizzare un opportuno sottoprogramma di tipo

BLOCK DATA. Ricordiamo che non è consentita la predefinizione di entità chefigurano in un blocco COMMON non etichettato.

L'unico scopo dei sottoprogrammi BLOCK DATA è quello di predefinire entitàche fanno parte di blocchi COMMON etichettati; essi sono quindi sottoprogramminon eseguibili che non possono essere utilizzati da altre unità di programma in

fase di esecuzione ma vengono trattati direttamente in fase di compilazione.La prima frase di un sottoprogramma BLOCK DATA ha la forma seguente:

BLOCK DATA nome

dove:

• BLOCK DATA è la parola chiave che identifica la frase;

• nome è un nome simbolico che può essere omesso. Se presente, nome è il

nome simbolico che identifica il sottoprogramma e lo distingue da tutte le altre

unità di programma; esso non può essere usato a nessuno scopo nel corpo del

sottoprogramma. In un programma possono esistere più sottoprogrammi di tipoBLOCK DATA con nomi diversi ed uno solo senza nome.

Il corpo di un sottoprogramma BLOCK DATA deve terminare con la frase

END e può contenere oltre a questa soltanto frasi di specificazione di tipo,frasi IMPLICIT, PARAMETER, DIMENSION, COMMON, EQUIVALENCE,SAVE (cfr. cap. 17) e, naturalmente, frasi DATA.

Esempio 16.16. Il sottoprogramma seguente

BLOCK DATACHARACTER • 6 CAR, MOTS(150)REAL A(IO, io), B(IO)COMMON / BLOCI / A, B,/ BLOC2 / MOTS,CAROATA A, B /110.0.5/, MOTS/150. 'INIZIO'/END

permette di predefinire con i valori presenti nella frase DATA i contenuti dellelocazioni di memoria che costituiscono il blocco COMMON di nome BLOCl,

Page 167: Fortran

I,! 326

identificate in questa unità di programma come elementi delle variabili dimensio­

nate A e B. Ancora, la frase DATA predefinisce gli elementi del vettore carattere

MOTS che fa parte del blocco COMMON di nome BLOC2, ma non la variabile

CAR che occupa le ultime sei unità di memoria del blocco. E' evidente che

i valori preassegnati in questo sottoprogramma alle variabili A, B sono direttamen­

te utilizzabili all'inizio della esecuzione da tutte le unità di programma al cui

interno sia definito un blocco COMMON di nome BLOCl; queste unità potranno

fare riferimento a tali valori con i nomi locali usati per identificare le celle del

blocco. Analogamente i valori memorizzati negli elementi del vettore MOTS

sono disponibili all'inizio dell'esecuzione per tutte le unità di programma che

fanno riferimento al blocco COMMON di nome BLOC2.

Esempio 16.17. Consideriamo il sottoprogramma:

BLOCK DATA BLOCDCHARACTER * lO SETTIM (7), MESE (12)INTEGER GMESE(l2)COMMUN I NOMI I SETTIM, MESE, I GIORNI I GMESEDATA SETTlM I 'LUNEDI"', 'MARTEDI"', 'MERCOLEDI''', 'GIOVEDI'",

*'VENERDI"', 'SABATO', 'DOMENICA' l, MESE I 'GENNAIO', 'FEBBRAIO'.*'MARZO', 'APRILE', 'MAGGIO', 'GIUGNO', 'LUGLIO', 'AGOSTO',*'SETTEMBRE', 'OTTOBRE', 'NOVEMBRE', 'DICEMBRE' I,*(GMESE(I), I = 1,12) I 31, 28, 31,30, 31 ,30, 2 * 31,30,31,30,31 I

END

Tale sottoprogramma BLOCD predefinisce tutti gli elementi dei vettori carat­

tere SETTIM e MESE e quelli del vettore intero GMESE; in altri termini ven­

gono predefinite tutte le unità di memoria dei blocchi COMMON di nomi NOMI

e GIORNI.

Si osservi che due o più sottoprogrammi BLOCK DATA in uno stesso pro­

gramma non possono fare riferimento a blocchi COMMON etichettati con lo

stesso nome.

327

Esercizi

16.1 Segnalare gli errori presenti nelle seguenti frasi COMMON:

a) COMMON A, B, C I BLl I N, A

b) COMMON Il N, M, I.

c) COMMON IVAR I D(l 00), B(I)d) DIMENSION A(200)

COMMON A(50)

e) DIMENSION V<N)

COMMON I VAR I V

f) FUNCfION BETA (X, Y)

COMMON MAT( l O, IO), X

g) CHARACTER * 80 FRASE

COMMON FRASE (l : 20)

h) CHARACfER * 30 PAESE

INTEGER N

COMMON PAESE, N

16.2 Rappresentare graficamente i blocchi COMMON definiti nel seguente pro­

gramma e i nomi usati nelle diverse unità per riferirsi alle locazioni deiblocchi

PROGRAM MAIN

COMMON A, X(5), YIBLl IC, Z(5, 5)/BL2/N, I, K

END

FUNCfION FUNZ (L, M)

COMMON A/BLl/C, Z(5, 5)

COMMON/BL3/ALFA

END

SUBROUTINE SUB

COMMON A, B, C, D, E, F, G/BL2/N(3)

COMMON/BL31ALFA

END

16,3 Se in una unita dI programma il blocco COMMON di nome PROVA è de­finito dalla frase

COMMON I PROVA I C(5. 4), A

con C ed A reali, indicare quali fra le seguenti definizioni possono esserepresenti in un'altra unità dello stesso programma:

Page 168: Fortran

328 329

a) COMMON / PROVA / C(5, 5), Ab) COMMON / PROVA / A(5), B(5), C(5, 2), D

c) COMMON / PROVA / C(5, 4)

d) COMMON / PROVA / X(2l)e) COMMON / PROVA / X(5), Y(5), Z(5), W(5)

f) COMMON / PROVA / A, C(5, 4)

g) COMMON / PROVA / M(2l)

16.5 Scrivere un programma che, fissato Q = 15 e due vettori u e v di IRn. usiil sottoprogramma MF2 dell'esempio 15.16 per determinare fra i punti

wk = ~ u + ( l - ~) v, O~ k ~ Q,quello a cui corrisponde il più piccolo

valore della norma euclidea della funzione data F n (x). Questa funzione

associa ad un vettore x di componenti xl' ... , xn

il vettore Y le cui compo­nenti Yl' ... , Yn sono definite da:

16.6 Modificare il sottoprogramma MAXMIN dell'esempio 14.3 e il programma

principale dell'esempio 14.8 in modo che lo scambio di informazioni fra le

due unità di programma avvenga tramite blocchi COMMON.

Si vuole che il programma risolva il problema per n = 2, 3,4,5; in ogni caso

il vettore u deve avere elementi tutti uguali a 0.5 e il vettore v deve avereelementi tutti uguali a 1. Inoltre si deve definire un solo sottoprogramma

che realizzi le funzioni F2(x), F3(x). F4(x) e Fs(x). (Suggerimento: fareuso della frase COMMON, cfr. esempio 16.7).

I :, I\ !

per i = 2, ... , n

per i = 1n

Yj =- 1 + nXjj= I

n

Yj = xi + L Xj - (n + 1)j= I

16.7 Modificare la funzione esterna MMV e il programma principale USOMMVdell'esempio 15.8 in modo che:

a) soltanto il vettore X resti fra gli argomenti muti di MMV e il valore di

N venga trasmesso tramite un blocco COMMON;

b) tutte le informazioni fra le due unità di programma vengano trasmesseattraverso blocchi COMMON.

16.8 Scrivere opportune frasi dichiarative per soddisfare le seguenti richieste:

a) due matrici rettangolari specificate dalla frase

REAL A(20, 20), B(20, lO)

si sovrappongono in modo tale che gli ultimi 200 elementi di A,coincidonocon gli elementi di B;

b) gli elementi di una matrice MAT di lO righe e lO colonne sono indivi­

duabili come elementi di un vettore MATV ET ;

c) i tre piani della variabile VAR3 dichiarata come

REAL VAR3 (lO, 10,3)

possano essere trattati come 3 matrici di lO righe e lO colonne.

PRIMA TERZA SESTA NONA

l(l ) M(l,l) I K(l)

1(2) M(2,1) J K(2)

1(3) M(3,1) K K(3)

1(4) M(1,2) M(l) L(l)

1(5) M(2,2) M(2) L(2)

1(6) M(3,2) M(3) L(3)

1(7) M(1,3) L(4)

1(8) M(2,3) L(5)

1(9) M(3,3) L(6)

1(10) M(I,4)

I( Il) M(2,4)

1(12) M(3,4)

Figura 16.11. Rappresentazione di un bloccoCOMMON non etichettato relativo all'esercizio 16.4.

16.4 Scrivere delle opportune frasi dichiarative che possano essere inserite

nelle unità di programma PRIMA, TERZA, SESTA, NONA in modo tale

da realizzare la spartizione del blocco COMMON non etichettato rappre­

sentata in fig. 16.11.

---------- ~--stl----------------

Page 169: Fortran

END

330

FUNCfION FUNZ (Y)

DIMENSION Z(3)

COMMON 1BL2 1X(5)EQUIVALENCE (X(2), Y)

l.. 'jJ"

l16.9 Indicare se sono corrette le sequenze di istruzioni qui indicate:

a) COMMON A, B, X( io: d) PROGRAM MAINEQUIVALENCE (B, X( I)) COMMON I BL2 1X(5)

b) COMMON A, B, X(lO)DIMENSION Y(lO)EQUIVALENCE (A, C), (X(5), Y(3))

c) PROGRAM MAIN

COMMON 1BLI 1X(5)

END

,17USO flessibile dei sottoprogrammi

SUBROUTINE SUBCOMMON 1BLI 1X(5)EQUI VALENCE (X(3), Y(3))

END

END

e) SUBROUTINE SUB I

COMMON 1BU 1X(5)

END

FUNCTION FUNZ I (Y)DIMENSION Z(3)

COMMON 1BU 1X(5)EQUIV ALENCE (X (4), Z( I))

END

17.1. Punti di ingresso secondari: l'istruzione ENTRY

L'istruzione ENTRY, non prevista in F66, è una frase non eseguibile che può

essere usata nel corpo di un sottoprogramma per evidenziarne dei punti particolari,

detti punti di ingresso secondari. ciascuno dei quali è identificato da un nome sim­

bolico e da una lista di argomenti muti. L'importanza di tali punti è legata al fatto

che un sottoprogramma può essere attivato facendo riferimento al nome di un

punto di ingresso secondario individuato da una frase ENTRY che compare

nel suo corpo. In questo caso lo scambio di informazioni fra l'unità di programma

chiamante e il sottoprogramma avviene tramite la lista di argomenti specificata

per il punto di ingresso secondario e l'esecuzione del sottoprogramrna inizia dalla

frase che segue immediatamente la frase ENTRY (cfr. fig. 17.1).

Figura 17.J. Trasferimento del controUo dell'esecuzione fra unità di programma chiamante esottoprogramma tramite un punto di ingresso secondario.

16.10 Scrivere la frase DATA che definisce come 1.5 il valore iniziale degli ele­

menti di un vettore V di lunghezza 15.

16.11 Scrivere la frase DATA che definisce come Ogli elementi della sottomatrice

triangolare superiore di una matrice MAT di 4 righe e 4 colonne.

16.12 Scrivere la frase DATA per predefinire due variabili di tipo carattere dinome TITOLO ed ESEMP con le stringhe 'INIZIALIZZAZIONEvDATI'

e 'TERZOvESEMPIO'.

16.13 Trovare gli eventuali errori nelle seguenti frasi:

a) DAI A I, K, LI 2 * 31b) DATA (V(I), I = K, IO) 1 IO. Il

c) LOGICAL LI

CHARACfER • 4 CARTADATA LI, CARTA /. TRUE., 'FIORI'!

d) REAL REL (2 : 8, - 5 : 5)DATA (REL(I, 1), J = - 5,5), 1= 2, 8) 177. lO

Unità di programma chiamante Sottoprogramma

Page 170: Fortran

332

L'istruzione ENTRY ha la forma seguente:

ENTRY nome (m), ... , mn )

dove:

• ENTRY è la parola chiave che identifica la frase;

• nome è un nome simbolico e costituisce il nome del punto di ingresso se­condario. Tale nome deve essere diverso dal nome del sottoprogramma in cui la

frase ENTRY compare e dai nomi degli altri eventuali punti di ingresso secondari.

Inoltre esso deve essere diverso dai nomi delle altre unità di programma e dei

loro eventuali punti di ingresso secondari;

• m), ... , mn sono gli argomenti muti del punto di ingresso secondario e possono

avere le forme consentite per gli argomenti muti del sottoprogramma in cui la

frase ENTRY compare.

La lista di argomenti muti in una frase ENTRY può essere diversa da quella

presente nella prima frase del sottoprogramma. Un argomento muto specificato

in una frase ENTRY non può essere usato nelle frasi eseguibili che la precedono,

a meno che esso non sia utilizzato come argomento muto anche in una precedente

frase ENTRY o nella prima frase del sottoprogramma. In ogni caso le frasi dichia­

rative relative ai parametri muti di una frase ENTRY devono precedere la prima

frase eseguibile del corpo del sottoprogramma (cfr. appendice A3). Osserviamo a

tale proposito che se la lista di argomenti di una frase ENTRY comprende il nome

di una variabile dimensionata con dimensionamento variabile, essa deve anche

comprendere i nomi delle variabili intere che compaiono nel dichiaratore della va­

riabile, a meno che esse non figurino in una frase COMMON. Così, è corretto il

sottoprogramma segue nte:

SUBROUTINE SUB(A, M, V)REAL A(M, e), V(M)

ENTRY PUNTO(V, M)

END

mentre è sbagliato scrivere

SUBROUTINE S(lij(A. M, V)REAL A(M, e), V(M)

ENTRY PUNTO(V)

END

Una frase ENTRY può non prevedere argomenti muti; in questo caso essa può

333

avere una delle forme seguenti:

ENTRY nome ( )

ENTRY nome

Una frase ENTRY può comparire in qualunque punto nel corpo di un sotto­

programma, ma non tra una frase IF(c) THEN e la corrispondente frase END IF

oppure tra una frase DO e la corrispondente frase terminale. L'istruzione ENTRY

ha il solo scopo di definire la posizione, il nome e gli argomenti muti di un punto

di ingresso secondario; essa quindi è ignorata se viene incontrata durante l'esecu­

zione del sottoprogramma.

Il nome di un punto di ingresso secondario di un sottoprogramma può essere

usato in una unità di programma distinta da questo come argomento attuale in un

riferimento ad un altro sottoprogramma; in questo caso il nome deve comparire

in una frase EXTERNAL nell'unità di programma chiamante. Così è corretta

la situazione seguente nella quale il nome, PUNTO, di un punto di ingresso secon­

dario della funzione FUNC viene usato nel riferimento al sottoprogramma SUB

come argomento attuale corrispondente all'argomento muto EFFE:

PROGRAM MAINEXTERNAL PUNTO

CALL SUB(X, PUNTO)

END

SUBROUTINE SUB(X,EFFE)

Y = EFFE(X)

END

REAL FUNCTION FUNC(X\

E~TRY PUNTO(X)

END

Page 171: Fortran

r

:\

334

17.2. Punti di ingresso secondari di un sottoprogramma SUBROUTlNE

Il nome di un punto di ingresso secondario di un sottoprogramma di tipo

SUBROUTlNE non può comparire in nessuna frase del sottoprogramma diversa

dalla frase ENTRY che lo definisce.

Esempio 17.1. Date (n + 1) coppie di numeri reali (xi' Yi ) con i = O, l, ... , n

e xi diverso da xj

per i diverso da j, esiste un unico polinomio Pn(x) di grado mi­

nore o uguale di n, tale che Pn(xi) = Yi per i = O, l, ... , n. Pn(x) è detto poli­nomio interpolante le coppie di valori dati e può essere scritto nella forma:

Ao + AI(x - xo) + A2(x - xo)(x - xl) + + An(x - xo) (x - Xl) ... (X - xn- l)

dove Ao è uguale a Yo e i coefficienti Al' , An sono differenze divise calcola-

bili mediante i valori Xi' Yi' i = O, ... , n [9]. Assegnato un valore reale x, il valorep = Pn(x) può essere calcolato utilizzando l'algoritmo seguente:

l. Dati: x; (Xi' Yi) con i = O, l, ..., n;

2. Poni ~ = Yo e Ao = go

3. Per i = l, ... , n

3.1. Poni gi = Yi3.2. Per k = i - l, ..., O

3.2.1. Calcola gk = (gk + l - gk)!(x i - xk)3.3. Poni Ai =~

4. Poni P = An5. Per i = n - l, ..., O

5.1. Calcola P = P' (x - Xi) + Ai6. Risultato: P

7. Stop

Si può osservare che la determinazione dei coefficienti Ao' ..., An è indipen­

dente dal valore di x (cfr. istruzioni 2 e 3). Pertanto, quando si voglia calcolare

Pn(X) per più valori di X può essere conveniente eseguire una sola volta le istru­

zioni 2 e 3 ed eseguire invece per ogni valore di x le istruzioni 4, 5 e 6. Sulla base

di queste considerazioni si perviene alla scrittura del sottoprogramma POLINT

di seguito riportato. Gli argomenti muti nella prima fase di POLINT hanno il

seguente significato:

- X e Y sono vettori reali che contengono in ingresso i valori xo' ... , xn e Yo' ... ,

Yn rispettivamente;

- N è una variabile intera che contiene in ingresso il valore di n;

- XS è una variabile reale che contiene in ingresso il valore di x;

- A è un vettore reale che contiene in uscita i coefficienti Ao' ... , An;

- PN è una variabile reale che contiene in uscita il valore Pn(x);

- G è un vettore reale di servizio.

335

SUBROUTINE POLINT (X, Y, N, XS, A, PN, G)REAL X(O: N), Y(O : N), A(O : N), XS, PN, G(O : N)INTEGER N

C CALCOLODEI COEFFICIENTI A(O),..., A(N)G(O)= Y(O)A(O) = CIO)DO IO I = l, NG(I) = Y(I)DO 5 K = I - l, O, - IG(K) = (G(K + 1) - G(K» / (X(I) - X(K»)

5 CONTINUEA(I) = G(O)

lO CONTINUEC CALCOLODEL VALORE, PN, DELPOLINOMIO INTERPOLANTEIN XS

ENTRY VALPOL(X,N,XS,A.PN)PN = A(N)DO 15 I = N - l, O,- IPN = PN • (XS - X(I) + A(I)

15 CONTINUERETURNEND

Nel corpo del sottoprogramma figura la frase

ENTRY VALPOL(X,N,XS,A, PN)

che individua un punto di ingresso secondario di nome VALPOL e argomenti

muti X, N, XS, A, PN. Il significato dei parametri X, N, XS, PN è uguale a quello

degli omonimi argomenti presenti nella prima frase del sottoprogramma, mentre

il vettore A in questo caso deve contenere in ingresso i coefficienti Ao' ... , An'

Se il sottoprogramma viene utilizzato in una unità di programma chiamante

nel modo usuale, ovvero facendo riferimento al nome POLINT, la frase ENTRY

viene ignorata durante l'esecuzione e vengono calcolati i coefficienti Ao' ...,

An e il valore Pn(x). Se invece nell'unità chiamante si fa riferimento al nome del

punto di ingresso secondario, VALPOL, allora l'esecuzione del sottoprograrnma

inizia dalla frase che segue la ENTRY; così in questo caso viene calcolato il valore

del polinomio interpolante mentre i coefficienti Ao' ..., An sono assunti comedati in ingresso.

Riferimento ai punti di ingresso secondari di un sottoprogramma SUBROUTlNE

Un riferimento ad un punto di ingresso secondario di un sottoprogramma di

tipo SUBROUTINE è consentito in una unità di programma distinta da questo

ed avviene tramite la frase

CALL nome (al' ... , an )

Page 172: Fortran

336

dove:• nome è il nome del punto di ingresso secondario;

• al"'" an sono gli argomenti attuali che devono accordarsi in numero, ordinee tipo con gli argomenti muti del punto di ingresso secondario. Se il punto di in­gresso a cui si fa riferimento non prevede argomenti, la frase CALL può avere una

delle forme seguenti:

CALL nome ( )

CALL nome

Al momento dell'attivazione del sottoprogramma i parametri attuali vengono

associati ai parametri muti del punto di ingresso secondario secondo le modalitàviste nel cap. 15 e l'esecuzione del sottoprogramma inizia dalla frase che segue

la ENTRY.

Esempio l 7.2. Sia P4 (x) il polinomio di grado minore o uguale di 4 che interpolacinque coppie di valori reali (Xi' Yi) , con i = O, ...,4, assegnate. Si vuole scrivereun programma che permetta di calcolare e stampare i valori P4 (Xi)' con i = I,· .. , IO, dove i valori xl , ...,xlO sono dati.

Il programma CALPOL che segue, risolve il problema utilizzando il sottopro­gramma POLINT dell'esempio precedente. In CALPOL i valori xl' ...,x lO sonomemorizzati nel vettore XS, mentre xo' , x4 e Yo' ..., Y4 sono memorizzatirispettivamente in X e Y e i coefficienti Ao' , A4 in A.

PROGRAM CAlPOLDIMENSION X(5), Y(5), A(5), XS(IO), G(5)DATA N, NXS/4, 101READ-,X, YREAD -. XSCALL POLINT (X, Y, N, XS(I), A, PN, G)PRINT ISO, XS(1), PNDO 20 I = 2, NXSCALL VALPOL (X, N, XS(I), A, PN)PRINT ISO, XS(I), PN

20 CONTINUESTOP

ISO FORMAT (IX, 'PN(, EI3.6, ') =', EI3.6)END

Con la frase

CALL POLINT (x. Y, N, XS(l), A, PN, G)

il sottoprogramma POLINT viene attivato facendo riferimento alla sua frase ini­ziale. L'esecuzione di POLINT avviene quindi in modo sequenziale ignorando lafrase ENTR Y che fa parte del suo corpo. Al rientro nel programma chiamante

337

sono disponibili in A i valori dei coefficienti Ao' ..., A4 e in PN il valore del po­

linomio interpolante in xl'Successivamente, per ogni valore di I compreso fra 2 e lO si esegue la frase

CALL VALPOL (X, N, XS(I), A, PN)

In questo caso si fa riferimento al punto di ingresso secondario del sottopro­gramma, e pertanto i parametri attuali X, N, XS(1), A e PN vengono associatiagli argomenti muti X, Y, XS, A e PN specificati nella frase ENTRY nel sotto­

programma.. L'esecuzione di POLINT ha inizio in questo caso dalla prima frasesuccessiva alla ENTRY e i valori dei coefficienti Ao' ..., A4 contenuti in A sonoutilizzati come dati in ingresso. Al termine della esecuzione di POLINT il valo­re del polinomio interpolante in Xi è disponibile in PN.

17.3. Punti di ingresso secondari di un sottoprogramma FUNCTION

Il nome di un punto di ingresso secondario di un sottoprogramma FUNCTIONpuò comparire come nome di variabile in frasi eseguibili successive alla ENTRYche definisce il punto. Il tipo della variabile il cui nome coincide con il nome diun punto di ingresso secondario è detto tipo del punto di ingresso secondario e

può essere specificato mediante la sua lettera iniziale oppure mediante una frase

dichiarativa di tipo che deve precedere la prima frase eseguibile del sottopro­gramma (cfr. appendice A3).

Punti di ingresso secondari di tipo carattere

Un punto di ingresso secondario in una funzione esterna di tipo carattere deve

essere di tipo carattere e pertanto il suo nome deve comparire in una fraseCHARACTER che precede la prima frase eseguibile del sottoprogramma. La lun­ghezza specificata per il nome del punto di ingresso secondario deve essere ugualealla lunghezza della funzione; in particolare essa deve essere espressa medianteuno specificatore di lunghezza indefinita se la funzione ha lunghezza indefinita.

Punti di ingresso secondari di tipo diverso da carattere

In una funzione esterna che non sia di tipo carattere possono essere presentipunti di ingresso secondari di qualunque tipo, ma non di tipo carattere. Di solitotutti i punti di ingresso secondari hanno lo stesso tipo della funzione.

Supponiamo che tutti i punti di ingresso secondari di un sottopogrammaFUNCTION siano dello stesso tipo della funzione; allora durante l'esecuzionedel sottoprogramma il valore della funzione può essere memorizzato in una varia­bile il cui nome coincide con il nome di un qualunque punto di ingresso secon-

iI

nIIl

'II

1

;II

Page 173: Fortran

339338

dari o O con il nome della funzione, qualunque sia il nome usato per l'attivazione.

Da ciò segue che nel corpo del sottoprogramma almeno uno fra i nomi dei puntidi ingresso secondari o della funzione deve essere utilizzato come nome di varia­bile in frasi eseguibili che ne definiscano il valore. Va comunque tenuto presente

che il nome di un punto di ingresso secondario non può comparire in frasi che

precedono l'istruzione ENTRY che lo definisce, ad eccezione che in una frase

dichiarativa di tipo.

REAL FUNCTION NORMA (U, N)REAL NORMAP, U(N), MAX

C CALCOLO DELLA NORMA INFINITO DI UMAX = ABS(U(I)DO 5 1= 2, NIF (MAX.LT.ABS(U(I))) MAX= ABS(U(I))

5 CONTINUENORMA=MAXRETURN

C

REAL FUNCfION NORMA (U, N)ENTRY NORMAP (U, N, IP)

Esempio 17.3. Se u è un vettore di componenti ul' ... , un' la norma Il u 11_ è de­

finita dalla relazione

Si osservi che durante l'esecuzione di un sottoprogramma FUNCnON tutti inomi di variabile dello stesso tipo che vengono usati nel corpo del sottoprograrn­

ma e che coincidono con il nome della funzione o con il nome di un punto di

ingresso secondario identificano la stessa locazione di memoria.

Supponiamo ora che in una funzione esterna siano definiti dei punti di ingres­

so secondari il cui tipo non coincide con il tipo della funzione. In questo casoil risultato di ogni esecuzione del sottoprogramma deve essere un valore dellostesso tipo del nome .tramite il quale è avvenuta l'attil'azione. Il risultato deve

quindi essere memorizzato in una variabile del tipo suddetto il cui nome coincide

con il nome di un punto di ingresso secondario oppure con il nome della funzione.Inoltre, durante l'esecuzione non deve essere assegnato alcun valore a variabili

di tipo diverso dal nome tramite il quale è avvenuta l'attivazione e il cui nome

coincida con il nome di un punto di ingresso secondario oppure con il nome

della funzione.

ENTRY NORMAP(U, N, IP)C CALCOLO DELLA NORMA-P DI U

MAX = ABS(U(1)DO lO 1= 2, NIF (MAX.LT.ABS(U(I)) MAX= ABS(U(I))

lO CONTINUENORMAP=O.IF (MAX.EQ.O.) RETURN00151=I,NNORMAP= NORMAP+ (U(I)/MAX) •• IP

15 CONTINUENORMAP= MAX. NORMAP.. (1./IP)END

In questo sottoprogramma il nome della funzione, NORMA, e il nome delpunto di ingresso secondario, NORMAP, sono entrambi di tipo reale. Pertanto

il significato del sottoprogramma resta inalterato se nelle frasi che seguono l'i­struzione ENTRY si sostituisce il nome NORMAP con il nome NORMA. Sarebbe

invece sbagliato sostituire NORMA con NORMAP nelle frasi eseguibili che prece­dono la ENTRY.

altrimenti.

max lUi Ii c iO:; nIlull_=

Data Il u 11_ ' è possibile calcolare la norma ~ u Il p con p intero positivo, nel modo

seguente:

Il seguente sottoprogramma NORMA può essere utilizzato ner calcolare Il u 11­oppure Il u 1\ con p > O assegnato. Nel primo caso il sottoprogramrna deve

essere attivafo mediante il nome, NORMA. che compare nella prima frase, mentre

nel secondo caso deve essere attivato mediante il nome, NORMAP, del suo punto

di ingresso secondario. Gli argomenti muti U ed N nelle due frasi

rappresentano rispettivamente il vettore u di cui si deve calcolare la norma e la sua

dimensione n; l'argomento muto IP nella frase ENTRY contiene in ingresso il

valore di p.

l !

Page 174: Fortran

340

Riferimento a punti di ingresso secondari di una funzione esterna

Un riferimento ad un punto di ingresso secondario di una funzione esterna

è consentito in unità di programma distinte dalla funzione ed ha la forma se­

guente:

dove:• nome è il nome del punto di ingresso secondario;• al"'" a

nsono gli argomenti attuali che devono accordarsi in numero, ordine e

tipo con gli argomenti muti del punto di ingresso secondario. Se il punto d'in­

gresso secondario non prevede argomenti, il riferimento deve avere la forma

nome ( )

L'attivazione e l'esecuzione del sottoprogramma avvengono nel modo già descritto

nel paragrafo precedente per i sottoprogrammi SUBROUTINE.

Esempio 17.4. II seguente programma utilizza la funzione NORMA dell'esempioprecedente per calcolare IleO)1.. ,~cO) Il eleO) b, con i = l, ... , n, dove c(i)

indica l'i-esima colonna di una matrice reale C di ordine n = lO.

REAL NORMA, NORMAPPARAMETER (N = IO)DlMENSION C(N, N)READ .,CDOI5I=I,NCN = NORMA (C(1. I), N)CNI = NORMAP (C(l, I), N,I)CN2 = NORMAP(C(l, I), N, 2)WRITE (.,35) I, CN, CNI, CN2

15 CONTINUESTOP

35 FORMAT (IX, 'COLONNA N.', I2/IX, 'NORMA INFINITO:', EI3.6/• IX, 'NORMA-l:', Ell 6/IX, 'NORMA-2:', EI3.6)

END

Per effetto del riferimento NORMA(C( l, I), N) gli argomenti attuali C( l, I)

ed N vengono associati alli argomenti muti della prima frase del sottoprogramrna

REAL FUNCfION NORMA (U, N)

L'esecuzione del sottoprogramma procede quindi in modo sequenziale e ter­

mina quando viene eseguita l'istruzione RETURN che precede la frase

ENTRY NORMAP (U, N, IP)

341

Quando il sottoprogramma viene attivato mediante uno dei riferimentiNORMAP (C( l, I), N, l) e NORMAP (CO, I), N, 2), gli argomenti attuali vengo­

no associati a quelli muti della frase ENTRY e vengono quindi eseguite tutte leistruzioni che seguono questa frase. Si osservi che nel programma chiamante è

indispensabile la frase di specificazione

REAL NORMA, NORMAP

Dagli esempi svolti in questo e nel precedente paragrafo, possiamo concludere

che l'istruzione ENTR Y è uno strumento utile in due tipi di situazioni: quando in

un sottoprogramma si individua un blocco di istruzioni che seguono la prima frase

e che in alcune particolari utilizzazioni del sottoprogramma non devono essere

eseguite (cfr. esempio 17.1), oppure quando il corpo di un sottoprogramma è

costituito da due o più blocchi uno solo dei quali viene eseguito ad ogni attiva­

zione del sottoprogramma (cfr. esempio 17.3). Nel seguito del capitolo vedremo

altre situazioni in cui l'istruzione ENTRY può essere vantaggiosamente utilizzata.

17.4. Le variabili interne di un sottoprogramma e l'istruzione SAVE

NelIe istruzioni che compongono il corpo di un sottoprogramma si utilizzano

spesso nomi simbolici che identificano variabili interne o locali al sottoprogram­ma, ovvero variabili il cui contenuto non è oggetto di scambio di informazionicon l'unità di programma chiamante. Più precisamente, le variabili interne sono

tutte quelle variabili i cui nomi non compaiono come argomenti muti nella primafrase del sottoprogramma o in qualche frase ENTRY e che non fanno parte di un

blocco COMMON. Durante l'esecuzione del sottoprogramma i nomi delle varia­

bili interne identificano delle locazioni di memoria il cui contenuto può essere

definito ed utilizzato dal sottoprogramma stesso. II periodo di tempo durante il

quale il nome di una variabile interna identifica una particolare zona di memoria

è limitato al tempo che intercorre fra l'attivazione del sottoprogramma e il rientro

nell'unità di programma chiamante. Pertanto se un sottoprogramma viene utiliz­

zato più volte durante l'esecuzione del programma, non vi è alcuna garanzia che

il valore delIe sue variabili locali resti inalterato da una chiamata all'altra. Se si

desidera che ciò avvenga per alcune variabili interne, occorre specificare i loro no­

mi in una frase dichiarativa SAVE nel corpo del sottoprogramma. In questo casol'istruzione SAVE può' avere la forma seguente:

SAVE v}' ... , vn

dove:• SAVE è la parola chiave che identifica la frase;

• v}' ... , vn sono i nomi delle variabili interne, dimensionate e non dirnen-

IlII

11

________________--..+--------..-------------1

Page 175: Fortran

342

sionate, di cui si vuole che sia mantenuto il valore al termine dell'esecuzione del

sottoprogramma.

Esempio 17.5. Sia dato un problema ai valori iniziali per un sistema di equazioni

differenziali ordinarie nella forma

\ y'(t) = f(t, y(t))

l y(to) = Yo

dove y(t), per ogni t nell'intervallo [to' te], è un vettore di ]R." e f(t, y(t)) è una

funzione a valori in JR" tale che il problema ammette un'unica soluzione y(t).

Esistono molti metodi numerici che consentono di approssimare i valori y(t j )

che la soluzione assume su un insieme di punti ti' con i = l, ... , N, dove

to

< ti < ... < tN = te (cfr. [9] e [lO)). Il sottoprogramma RK:S, la. cui listacompleta si trova in [lO], utilizza un particolare metodo numenco (di Runge­

Kutta-Fehlberg) per calcolare un vettore u j che approssima y(t j ) avendo come

dato un vettore ui_ I che approssima y(ti_ 1) · Posto Uo = Yo assegnato, il sotto­

programma deve essere richiamato N volte consecutive per calcolare ul' ... , uN'

SUBROUTINE RKFS (F, NEQN, Y, T, TOUT, RELERR, ABSERR,• IFLAG, yP, H, Fl, F2, F3, F4, F5, SAVRE, SAVAE, NFE, KOP. INIT,

• JFLAG, KFLAG)

MFLAG = IABS (IFLAG)

IF (MFLAG.NE.l) GOTO 20C PRIMA CHIAMATA - SI CALCOLANO EPS E U26

EPS = 1.0EPS = EPS/2.0EPSPI = EPS + 1.0IF (EPSl.GT.l.) GOTO 5026 = 26.0 • EPSGOTO 50

C CHIAMATE SUCCESSIVE20 CONTINUE

50 CONTINUE

RER = 2.• EPS + REMIN

HMIN = 026 • ABS (T)

END

343

Fra gli argomenti muti di RKFS, il significato dei quali è spiegato in [lO],

Y è un vettore che contiene in ingresso ui_ I e in uscita uj' mentre T e TOUT

contengono in ingresso ti_ I e ti rispettivamente. Inoltre IFLAG è un indicatoreche può assumere in ingresso e in uscita diversi valori; in particolare alla prima

chiamata di RKFS il valore assoluto di IFLAG in ingresso deve essere uguale a

l, mentre deve essere diverso da l alle chiamate successive. Osserviamo che nelcorpo del sottoprogramma vengono utilizzate due variabili locali, EPS e U26,

i cui valori vengono calcolati una volta per tutte alla prima chiamata. Evidente­

mente, RKFS può fornire risultati corretti alle chiamate successive alla prima sol­

tanto se il sistema di calcolo con cui si lavora mantiene inalterato il valore delle

variabili interne anche dopo il rientro nella unità di programma chiamante. Per

avere la garanzia che questo succeda per qualunque sistema di calcolo occorre

inserire tra le frasi dichiarative del sottoprogramma l'istruzione seguente:

SAVE EPS, U26

Esempio 17.6. Consideriamo il seguente sottoprogramma:

SUBROUTlNE PARAM (ALFA)SAVE AA=ALFARETURNENTRY FALFA (X, Y)Y = 0.5. (EXP(ALFA. X) - EXP(- ALFA. X))RETIJRNEND

L'attivazione di questo sottoprogramma mediante la prima frase consente di

memorizzare nella variabile locale A il valore dell'argomento attuale corrisponden­

te all'argomento muto ALFA; essendo presente la frase SAVE A, tale valore viene

conservato anche dopo il rientro nell'unità di programma chiamante. Così il valo­

re di ALFA è disponibile per l'esecuzione del sottoprogramma se questo viene

successivamente attivato tramite il punto di ingresso secondario definito dallafrase

ENTRY FALFA (X, Y)

Un esempio di utilizzazione del sottoprogramma PARAM è tratteggiato quidi seguito:

Page 176: Fortran

344

PROG RAM MAINEXTERNAL FALFA

A=O.lCALL PARAM (A)CALL SUB (FALFA, ...)

END

SUBROUTINE SUB (F, ...)

CALL F(X, Y)

END

Il programma principale attiva il sottoprogramma PARAM in modo che venga

memorizzato nella variabile locale A il valore 0.1; successivamente il sottopro­

gramma SUB richiama il sottoprogramma PARAM mediante il nome del puntodi ingresso secondario FALFA.

Esempio 1 7. 7. E' noto che una funzione ricorsiva può essere tradotta in un sotto­programma che fa uso di cicli-DO e di particolari strutture di dati dette pile [15].

Una pila è un insieme ordinato di elementi sul quale sono consentite le seguentioperazioni:

a) aggiungere un elemento in testa alla pila;

b) prelevare un elemento dalla testa della pila.

Per dare un'idea, necessariamente semplificata, di come può essere costruito

un sottoprogramma non ricorsivo come risultato della traduzione di una funzione

ricorsiva, consideriamo la funzione min, definita neli' esempio 1.13, che calcola

l'elemento minimo di un vettore. Ricordando che, indicato con [al' ... , an] il

vettore dato, se ne possono evidenziare il primo e i restanti elementi usando la

notazione [al Iz] con z = [a2, ..., an] (cfr. esempio 1.11), la definizione dellafunzione min è la seguente:

min ([al)) = al

min ([al' a2 )) = se al < ~ al/ora al altrimenti a2

min ([ali z)) = min ([al' min (z)))

In questo caso gli elementi della pila sono gli indici degli elementi del vettore

a = [al' ... , an]· Il sottoprogramma non ricorsivo prevede due fasi. Nella primafase si provvede a definire gli elementi della pila, simulando in questo modo lechiamate della funzione min presenti nella parte ricorsiva della definizione; in-

345

fatti da questa si ottiene che

min ([ali z l) = min ([al' min ([a 2, min ([a 3, .•.»])

Nella seconda fase si utilizza la parte non ricorsiva della definizione per calcolare

il valore della funzione. Ciò avviene nel modo seguente: vengono prelevati dallapila l'elemento in testa e quello immediatamente precedente e vengono confron­

tati fra loro gli elementi del vettore ad essi corrispondenti; l'indice del minimo

fra questi due elementi viene quindi aggiunto alla pila e diventa il nuovo elemento

di testa. Si procede così finché la pila non contiene un solo indice che necessa­

riamente è quello dell'elemento minimo cercato.Per realizzare le operazioni sopra tratteggiate si utilizzano due sottoprogrammi:

la funzione esterna MIN l che calcola il minimo e il sottoprogramma AGG, di tipo

SUBROUTINE utilizzato dalla prima per eseguire le operazioni sulla pila. I due

sottoprogrammi possono essere utilizzati per calcolare min ([al' ... , an j) con

l ~ n ~ 100.

SUBROUTINE AGG(K)INTEGER PILA (100), TESTASAVE PILA, TESTADATA TESTA /0/

C AGGIUNT A DI UN ELEMENTO IN TEST A ALLA PILAIF (TESTA.GE.lOO) THEN

PRINT -. 'LA PILA Eli PIENA'STOP

ELSETESTA = TESTA + lPILA (TEST A) = KRETURN

ENDIFC PRELIEVO DELL'ELEMENTO IN TEST A ALLA PILA

ENTRY PREL (K)IF (TESTA.LT.I) THEN

PRINT -. 'LA PILA Eli VUOTA'STOP

ELSEK = PILA (TESTA)TESTA = TESTA - lRETURN

ENDIFEND

L'argomento muto K nella prima frase del sottoprogramma contiene in ingres­

so il valore che deve essere aggiunto in testa alla pila, mentre nella frase

ENTRY PREL (K)

esso contiene in uscita il valore che è memorizzato nell'elemento in testa alla pila.

Ii

1 I:1

l

______________-...-__.....--rrtL-------------------.

Page 177: Fortran

----------------- -

346

II vettore intero PILA che contiene la pila e la variabile intera TEST A che contie­ne la posizione in PILA dell'elemento di testa sono variabili locali il cui valore vie­ne conservato da una chiamata all'altra per effetto delIa presenza della frase

SAVE PILA, TESTA

II valore di TESTA viene aggiornato ad ogni chiamata del sottoprogramma. Inparticolare, se questo viene attivato tramite la prima frase, il valore di TEST A vie­

ne incrementato di una unità e viene posto uguale a K il valore di PILA (TESTA);se invece il sottoprogramma viene attivato tramite il punto di ingresso secon­dario PREL, il valore di PILA (TESTA) viene assegnato al parametro di uscitaK e successivamente il valore di TESTA viene decrementato di una unità.

La funzione esterna MIN1 utilizza il sottoprogramma AGG per calcolare ilminimo fra i primi N elementi di un vettore A di 100 elementi.

REAL FUNCTION MINI (A, N)REAL A(lOO)

C PRIMA FASE; SI MEMORIZZANO NELLAPILA GLI INDICI I, ... , NDO IO I = I, NCALL AGG(I)

IO CONTINUEIF (N.EQ.I) GOTO 30

C SECONDA FASE: SI RIPERCORRE LA PILA ALL'INDIETRODO 20 I = N, 2, - I

C GLI ELEMENTI DI A CORRISPONDENTI AI DUE ELEMENTI DIC TESTA DELLA PILA VENGONO CONFRONTATI. L'INDICE DELC PIU' PICCOLO FRA I DUE DIVENTALA NUOVA TESTA DELLA PILA

CALL PREL (KI)CALL PREL (K2)IF (A{KI).LT.A(K2» THEN

CALL AGG(KI)ELSE

CALL AGG(K2)ENDIF

20 CONTINUEC LA PILA CONTIENE L'INDICE DELL'ELEMENTO MINIMO DI AC LA SECONDA FASE HA TERMINE

30 CONTINUECALL PREL (K)MINI = A(K)RETURNEND

Ricordiamo che una variabile interna ad un sottoprogramma predefinita me­diante una frase DATA conserva il suo valore per la durata dell'esecuzione del­l'intero programma, soltanto se questo valore non viene modificato nel sottopro­gramma. In caso contrario, affinché il valore venga mantenuto fra due successive

347

chiamate del sottoprogramma, è necessario che il nome della variabile figuri in

una frase SAVE nel corpo del sottoprogramma.

17.5. I blocchi COMMON etichettati e l'istruzione SAVE

Una situazione analoga a quella descritta nel paragrafo precedente per le varia­bili interne ad un sottoprogramma, si verifica anche per i blocchi COMMONetichettati. Più precisamente, quando termina l'esecuzione di un sottoprogrammache ha accesso ad un blocco COMMON etichettato i valori memorizzati nelblocco vengono conservati soltanto se allo stesso blocco ha accesso anche l'unitàchiamante oppure un'altra unità che, attraverso una catena di chiamate, ha provo­cato l'attivazione del sottoprogramma. In caso contrario non si ha la garanziache i valori memorizzati nel blocco vengano conservati, e si dice che il blocco di­venta indefinito. Evidentemente, un blocco COMMON presente anche nel pro­gramma principale non diventa mai indefinito nel corso dell'esecuzione del pro­gramma. Inoltre non diventa mai indefinito il blocco COMMON non etichettato.

Esempio 17.8. In un programma costituito dal programma principale MAIN e daiquattro sottoprogrammi SUB l, SUB2, SUB3, SUB4, sono definiti tre blocchiCOMMON etichettati di nomi ETMI24, ETI3, ET34. Supponiamo che I'organiz­zazione del programma possa essere schematizzata nell'albero delle chiamate difig. 17.2, dove in ogni rettangolo si sono riportati, oltre al nome dell'unità di

programma, i nomi dei blocchi COMMON a cui essa può accedere. Dalla figura

possiamo dedurre quanto segue:

Figura 17.2. Albero deUe chiamate e accesso ai blocchi COMMON nell'esempio 17.8.

Page 178: Fortran

348

- II blocco COMMON/ETM 124/ non diventa mai indefinito dal momento che è

utilizzato nel programma principale;

- II blocco COMMON/ET 13/ non diventa indefinito al termine della esecuzionedi SUB3; infatti a questo blocco ha accesso anche il sottoprogramma SUB l che,avendo richiamato SUB2, ha provocato l'attivazione di SUB3. Pertanto i valorimemorizzati nel blocco vengono conservati quando termina l'esecuzione di SUB3e il blocco diventa indefinito soltanto al termine dell'esecuzione di SUB l, quando

il controllo ritorna al programma principale;

- II blocco COMMON/ET34/ diventa indefinito sia al termine della esecuzione di

SUB3 che al termine dell'esecuzione di SUB4. Evidentemente in questo caso non

vi è più la garanzia che le informazioni memorizzate nel blocco da uno dei duesottoprogrammi vengano ritrovate intatte dall'altro; ciò può comportare una to­

tale perdita di significato del blocco se questo viene utilizzato come mezzo per

la trasmissione di informazioni fra i due sottoprogrammi.

Situazioni come quella ora descritta possono essere evitate dichiarando nel pro­

gramma principale tutti i blocchi COMMON etichettati che vengono utilizzati dal­

le varie unità di programma. In F77 si può usare allo stesso fine l'istruzione SAVE

la cui forma generale è infatti la seguente:

SAVE lista

dove ogni elemento della lista può essere il nome di una variabile interna oppure il

nome di un blocco COMMON racchiuso fra sbarre e due successivi elementi dellalista sono separati mediante una virgola.

Se il nome di un blocco COMMON figura in un'istruzione SAVE in una unitàdi programma, le variabili del blocco conservano il loro valore al termine dell'ese­cuzione di questa unità. Così, per esempio, l'istruzione

SAVE A, B, /COMC/, K l

serve a specificare che le variabili interne A, B e K l e le variabili facenti parte del

blocco COMMON/COMC/ devono mantenere il loro valore anche dopo la fine

dell'esecuzione del sottoprogramma in cui la frase compare. Notiamo che se il

nome di un blocco COMMON fa parte della lista di un'istruzione SAVE in una

unità di programma, esso deve figurare in un'istruzione SAVE anche in tutte le

altre unità di programma che hanno accesso al blocco.

L'istruzione SAVE in un sottoprogramma può anche ridursi alla sola parola

chiave

SAVE

In questo caso tutte le variabili interne e le variabili di tutti i blocchi COMMONetichettati a cui il sottoprogramma ha accesso mantengono il loro valore al termi­ne dell'esecuzione del sottoprogramma.

349

Esercizi

17.1 Individuare gli errori presenti nei seguenti sottoprogrammi:a) SUBROUTINE MAT (A, NMAX, N)

REAL A (NMAX, N)

ENTRY SUBMAT(A, N)

END

b) SUBROUTINE SUB (A, B, C)

D=l.

ENTRY SUBS (D)

END

c) FUNCTION FUNZ (X, Y)

A = DER (X, Y)

ENTRY DER (X, Y)

END

17.2 Modificare il sottoprogramma POLINT dell'esempio 17.1 in modo tale daottenere un nuovo sottoprogramma che non faccia uso dell'istruzione ENTRY

e che, come POLINT, possa essere utilizzato per calcolare i coefficienti

Ao' ..., An del polinomio interpolante e il valore Pn(x) oppure solo per cal­colare Pn(x). (suggerimento: inserire un indicatore fra gli argomenti muti).

17.3 Modificare, nello stesso spirito del precedente esercizio, il sottoprogrammaNORMA dell'esempio 17.3.

17.4 Scrivere, facendo uso dell'istruzione ENTR Y, un sottoprogramma che possa

essere usato per calcolare, assegnato un valore di x, il valore della funzionefl x) definita da:

f(x) = x - sen (x - l) - l

oppure il valore della derivata ['(x), definita da

f'(x) = l - cos (x - l)

I.

Page 179: Fortran

k = O, l, ...,4.

350

17.5 Scrivere, facendo uso dell'istruzione ENTRY, un sottoprogramma mediante

il quale si possa calcolare, dato x, il valore di f(x) oppure i valori di f(x) e

f''(x), dove f(x) è la stessa funzione del precedente esercizio.

17.6 Scrivere un programma che, utilizzando il sottoprogramma dell'esercizio

17.4, permetta di calcolare e stampare i valori di f(x i ) e f'(x i) per Xi == 0.5 + i 0.01, i = O, ..., lO.

17.7 Scrivere un programma che, utilizzando il sottoprogramma dell'esercizio

17.5, permetta di calcolare e stampare i primi cinque termini della succes­

sione {xk }, dove Xo = O e i restanti termini sono definiti da

f(xk

)

x =x ---k+l k f'(x

k)

II programma deve interrompersi se, per un valore di k, risulta r'(xk) = O.

17.8 II sottoprogramma PARAM dell'esempio 17.6 deve necessariamente esseredi tipo SUBROUTINE e non può essere di tipo FUNCfION. Spiegare il

motivo di tale affermazione.

17.9 Spiegare il significato che assume il sottoprogramma PARAM dell'esempio

17.6 se si elimina dal suo corpo la frase RETURN che precede l'istruzione

ENTRY. Scrivere un programma principale che utilizzi il sottoprogramma

PARAM nella versione così modificata per calcolare i valori della funzione

y = 0.5 (eQ X - e(- QX)

con Cl' = 0.01 per i seguenti valori di x: O, 1, 2, 3, 4.

"

18Trattamento dei files

18.1. Introduzione

Abbiamo fin qui trattato le operazioni di I/O procedendo dalla loro formapiù semplice, le frasi di I/O guidate dalla lista (cfr. cap. 8), fino ad una formaun po' più complessa, le frasi di I/O con formato (cfr. cap. 13).

Tali argomenti non esauriscono l'esposizione del complesso delle istruzioniche il F77 offre all'utente per una completa e sofisticata gestione del meccanismodi I/O.

In generale una operazione di I/O comporta la trasmissione di informazionisotto forma di records da o verso unità (o mezzi) di I/O cui sono associati deifiles. Tale trasmissione può avvenire sotto il controllo di formato (cfr. cap. 13)oppure senza il controllo di formato. Ancora, la modalità di accesso ad un filepuò essere sequenziale o diretta.

Inoltre, tali files possono essere rappresentati su supporti esterni alla memoriacentrale, ad esempio su una stampante o video, su nastro o disco magnetico, oall'interno della memoria centrale.

Da quanto detto si vede quanto possano essere diversificate le operazioni di

I/O a seconda delle necessità e, conseguentemente, quante informazioni debbano

essere fornite prima di un'operazione di I/O per stabilire le varie caratteristichedel file associato all'unità usata nell'operazione stessa.

Una operazione di I/O può poi svolgersi senza alcun errore oppure no: può

essere allora utile gestire in qualche modo queste eventualità. Vedremo che la

forma generale delle istruzioni di I/O prevede anche tali possibilità.

18.2. Records e files

Nel cap. 13 abbiamo esaminato le varie possibilità disponibili in F77 per rea­lizzare le richieste dell'utente che voglia fornire dati e vedere i risultati dell'ese­

cuzione di un certo programma avendo in mente la gestione dei mezzi di I/O chetrasmettono informazioni strutturate sotto forma di files di tipo sequenziale i

Page 180: Fortran

352

cui records sono costituiti da sequenze di caratteri con una prestabilita confi­

gurazione: i records con formato.Una prima definizione di records e files è già stata data nel cap. 13. Conviene

qui riprendere questi concetti per poter descrivere le rimanenti possibilità per

la gestione di operazioni di I/O «meno intuitive» di quelle già viste.I records previsti in F77 sono di tre tipi:

a) records con formato, costituiti da sequenze di caratteri riconosciuti dal siste­

ma di calcolo;b) records senza formato, costituiti da sequenze di valori, nella forma di rappre­

sentazione interna;c) record endfile.

Nel cap. 13 abbiamo solo trattato i records di tipo a).

.Lìna sequenza di records tutti del medesimo tipo (a) o b» costituisce un file.

A loro volta, i files possono essere suddivisi in due categorie:

a) files esterni, rappresentati su supporti esterni alla memoria centrale dell'ela­

boratore;b) files interni, rappresentati all'interno della memoria centrale; sono usati

esclusivamente quale magazzino temporaneo di dati, la loro «vita» è quella del

tempo di esecuzione del programma in cui sono definiti come vedremo nel se­

guito.

Per quanto riguarda i files esterni, rappresentati su supporti magnetici, nastri

e dischi, occorre mettere in luce una profonda differenza fra i due tipi di suppor­

to magnetico.Il nas!ro magnetico è un supporto seque,!zitl/~, come lo sono una stampante,

una telescrivente, un video o un lettore di schede. Ciò implica che per accedere

ad un record del file occorre avere prima scorso tutti i records che si trovano pri­

ma di quello voluto; in altri termini, i records devono essere letti nel medesimo

ordine in cui sono stati scritti. Tale caratteristica comporta un certo dispendio

di tempo per lo scorrimento, avanti o indietro, del nastro per poter accedere al

record voluto.Su di un disco, al contrario, si può accedere ad ogni sua parte in un tempo

estremamente inferiore a quello necessario sul nastro: come vedremo più avantioccorre solo che la testina di lettura/scrittura si sposti di qualche centimetroavanti o indietro per posizionarsi sulla parte voluta.

Si dice allora che su tale mezzo le informazioni possono essere reperite ad

f!.c:..E~sso c!ire!to, per significare la differenza con il concetto di accesso sequenziale

visto sopra. Tale caratteristica del disco non impedisce che su di esso si possano

gestire files anche in modo sequenziale, mentre il viceversa non è possibile sui

nastri: questi consentono solo un accesso sequenziale.

353

Conseguentemente, i files possono essere files sequenziali o files ad accesso

diretto.Volendo allora leggere o scrivere informazioni su di un file esterno dovremo

specificare quale sia il modo di accesso al file, sequenziale o diretto, e se i suoi

records sono con o senza formato.Tali specifiche, insieme a diverse altre, vengono esplicitamente fomite tramite

la frase .~~Ia cui utilizzazione non è richiesta per alcuni mezzi esterni, adesempio i mezzi standard, per i quali il sistema assume implicitamente il modo di

accesso sequenziale e records con formato.

Records con formato e senza formato

I records con formato sono costituiti da una sequenza di caratteri tale da essere

facilmente compresa da un essere umano. Tali records sono scritti tramite le ope­razioni di uscita guidate dalla lista o sotto il controllo esplicito del formato.

Ancora, questi records possono anche essere creati senza l'esecuzione di un pro­gramma FORTRAN, ad esempio servendosi di programmi di «editing» general- I

mente disponibili nei moderni sistemi di calcolo.La lunghezza di un record con formato è data dal numero di caratteri che lo

compongono. Si noti che la conoscenza della lunghezza di un record è necessaria

quando il file cui il record appartiene sia dichiarato ad accesso diretto.

La trasmissione di un record con formato implica una conversione da rappre­

sentazione esterna ad interna o viceversa dei dati in esso contenuti; ciò compor­

ta un tempo non trascurabile. Se, d'altra parte, l'informazione scritta sul record

non deve essere letta da un essere umano, ma successivamente letta nel medesimo

o altro programma, non si presenta la necessità di dover convertire questa infor­

mazione da rappresentazione interna ad esterna o viceversa.

l/In questo caso, con grande risparmio di tempo, basta usare frasi di I/O senza il/'I controllo di formato per produrre o leggere records senza formato.

I Un record senza formato è costituito da una sequenza di valori rappresentati

~econdo modalità dipendenti dal sistema. In generale un valore è esattamente

111a rappresentazione interna di un dato; così un record senza formato può esseriiconsiderato la copia di una parte della memoria.

Frasi di I/O senza formato possono essere scritte semplicemente non riportando

l'identificatore di formato, ma solamente il riferimento all'unità di I/O come si

vede nelle frasi seguenti:

WRITE (8) A V, BV, CV

READ (9) X, Y

La prima fa sì che venga scritto il record costituito dai valori attuali delle varia­

bili AV, BV e CV sul file associato all'unità 8; la seconda ha invece l'effetto di

, II

Page 181: Fortran

354

leggere, dal file associato all'unità 9, un record che si suppone costituito da due

valori che, senza alcuna conversione, sono assegnati alle variabili X e Y.La lunghezza di un record senza formato è misurata in unità dipendenti dal

sistema; generalmente l'unità di misura è il byte o multiplo di byte. Così se ivalori di AV, BV e CV sono rappresentati su quattro by tes, il record prodottodalla frase WRITE sopra riportata risulta lungo 12 bytes.

Notiamo una importante differenza fra le frasi di I/O con formato e quellesenza.

Le prime, per effetto del controllo congiunto fra lista e specificazione di for- I

',mato, possono trasmettere più records; le seconde possono trasmettere un solo

((I(' \" record per volta.III Inoltre, la lunghezza della lista in una istruzione d'ingresso senza formato deve

Il;! iessere minore o uguale alla lunghezza della lista della frase di uscita che ha pro-

,'l'dotto il record che sta per essere letto.

Esempio 18.1. Affinché la frase

READ (9) X, Y

possa essere correttamente eseguita occorre che il record che sta per essere letto

sul file associato all'unità 9 sia costituito da almeno due valori.

Nel caso in cui la lunghezza della lista sia inferiore a quella del record che sta

per essere letto, i valori eccedenti sul record resteranno non letti.

Il record endfile e la frase ENDFILE

Il record endfile può essere posto solo come ultimo record di un file ed è pro­dotto con l'uso della frase speciale:

355

Il significato di questi specificatori verrà dato nel paragrafo successivo.

Notiamo che, comunque, l'unità riferita da u deve essere ad accesso sequen- , ! I

ziale. I

L'effetto principale dell'esecuzione della frase ENDFILE è quello di scrivere

sul file associato all'unità u il record speciale endfile. Ciò rende impossibile ogni

successivo tentativo di leggere da o scrivere su quel file senza avere prima scorsoall'indietro il file usando una frase BACKSPACE o REWIND (cfr. § 18.5).

E' molto comodo porre tale record alla fine di files sequenziali che devono es­sere successivamente riletti per facilitare tale rilettura completa senza dover con­

trollare la lunghezza del file da leggere. L'uso del record endfile verrà evidenziatonell'esempio 18.12.

18.3. La forma generale delle frasi di I/O

La forma generale delle frasi di I/O è la seguente:

rw (dista) lista-di-I/O

dove:

• rw è la opportuna parola chiave: READ per le operazioni di ingresso,WRITE per quelle di uscita;

• lista-di-I/O è la lista degli elementi i cui valori devono essere trasmessi; per lasua forma cfr. cap. 13;

• dista è la lista di controllo che fornisce informazioni sia circa l'unità diI/O che sulla natura e modalità di gestione dell'operazione.

L'effetto principale di un 'operazione di I/O è quello già ampiamente descrittonel cap. 13: la trasmissione di uno o piu records.

La lista di controllo

Tale lista è costituita dall'elenco di tutti o parte dei seguenti specificatori se­parati da virgole

I

l",l, \

ENDFILE u

oppure

ENDFILE (auxlista).

Nella prima forma u è l'espressione intera il cui valore denota il numero dell'u­

nità sulla quale il record deve essere scritto; nella seconda forma la lista auxlista

può contenere ciascuno dei seguenti specificatori separati da virgole e senz'altrolo specificatore relativo all'unità:

u

UNIT = uERR =s10STAT = v

gli specificatori u e UNIT = u sono equivalenti.

u

UNIT = uf

FMT= f

10STAT = sERR =sEND =sREC = n

Lo specificatore u oppure UNIT u, relativo all'unità di I/O, deve essere

Page 182: Fortran

356

sempre presente. In particolare, se esso è l'unico specificatore presente, la frase

in questione rappresenta una operazione di l/O senza formato sul file (sequenzia­

le) associato all'unità specificata.

Se la stringa UNlT = è omessa, allora lo specificatore u deve essere il primo ele­mento della lista di controllo. Lo specificatore u può avere una delle forme se­

guenti:

a} un'espressione intera il cui valore identifica l'unità di l/O interessata all'o­

perazione e quindi il file ad essa associato;

b) il carattere asterisco ... che denota l'opportuno mezzo standard;

c) uno dei seguenti elementi di tipo carattere: una variabile, un elemento di

variabile dimensionata, una sottostringa, una variabile dimensionata.

La specifica dell'unità secondo le forme a) e b) consente di gestire files esterni.Quella -~econdo la forma c) consente la gestione di files interni; le operazioni di

17C>;~iative a queste unità verranno descritte nel § 18.8.

In una operazione di l/O con formato deve essere presente uno dei seguenti( specificatori:

FMT = f oppure f

ILa stringa FMT = può essere omessa solo se è stata omessa la stringa UNlT =

nello specificatore d'unità, in questo caso l'identificatore di formato f dev~ essereil secondo elemento nella lista di controllo.

Si noti che se lo specificatore di formato è assente l'operazione di l/O avvienesenza il controllo di formato.

Esempio 18.2. Alcune frasi di l/O fra loro equivalenti:

READ (UNII = l, FMT = 50) A, B, CREAD (FMT = 50, UNII = l) A, B, CREAD (1, FMT = 50) A, B, CREAD (l,50) A, B, CREAD (I, 50) A, B, CREAD (l, '(3FlO.0)') A, B, CREAD (UNII = l, FMT = '(3FlO.0)') A, B, C

50 FORMAT (3FIO.0)

357

Si noti che fra tutte le forme di frasi di I/O dell'esempio 18.2 soloREAD( l ,50) A, B, C REA D (I, 50) A, B, C WRlTE (2, 60) A, B, C eWRlTE (J, 60) A, B, C sono consentite in F66.

Gli specificatori di

stato 10STAT = v

errore ERR = s

fine file END = s

sono opzionali e, se presenti, le relative parole chiave devono essere pureriportate.

Nello specificatore di stato 10STAT = v, v è un nome di variabile o elementodi variabile dimensionata di tipo intero. AI termine dell'operazione di l/O v assumeun determinato valore:

• zero, se l'operazione ha avuto termine normalmente;

• un intero positivo, se è occorso un errore, ad esempio di conversione di un

dato, oppure se il file associato all'unità specificata non ha opportune caratte­ristiche: è costituito ad esempio da records senza formato mentre l'operazione ècon formato;

• un intero negativo, se l'operazione in questione è un'operazione di ingresso ditipo sequenziale, nessun errore è avvenuto ma è stato incontrato il record endfile

non potendo così completare l'operazione di ingresso per mancanza di dati.

Il valore effettivo di v dipende dal sistema, e può essere controllato dopo l'ope­razione di l/O per poter decidere le opportune azioni successive.

Esempio 18.3. Uso dello specificatore 10STAT. Si consideri il seguente segmentodi programma:

READ (1,50, IOSTAT = KS) A, B, CIF (KS.LT.O) THEN

C FINE DEL FILE

ELSEC CONTINUAZIONE DELLA NORMALE ELABORAZIONE

ENDIFSTOP

50 FORMAT (3 EI3.6)END

nelle quali si suppone l = l.

WRITE (UNII = 2, FMT = 60) A, B, CWRIIE (J, '(IX, 3E13.6)') A, B, CWRIIE (FMT = 60, UNII = l + I) A, B, CWRIIE (2, 60) A, B, CWRIIE (J, 60) A, B, CWRIIE (UNII = 2, FMT = '(IX, 3E13.6)') A, B, C

60 FORMAT (IX, 3E13.6)

nelle quali si suppone J = 2 e l = l.

CELSE IF (KS.GT. O) THENCONDIZIONE D'ERRORE DURANTE LA LETTURA

Page 183: Fortran

358 359

Esempio 18.4. Simulazione dell'esempio 18.3 tramite gli specificatori ERR eEND.

La lista di controllo presente nella READ specifica che la lettura avviene dal

file associato all'unità l secondo le modalità di conversione date nella frase

FORMAT di etichetta 50; lo stato al termine dell' operazione è codificato nella

variabile intera KS e l'esecuzione procede in base al valore di KS che viene con­trollato nella struttura IF successiva.

Negli specificatori di errore ERR = s e di fine file END = s, s è l'etichetta diuna frase eseguibile appartenente alla medesima unità di programma.

Il significato di tali specificatori è il seguente: il controllo viene trasferito

all'istruzione etichettata con s se durante l'operazione si sia verificata una condi­

zione di errore per il primo o se, in lettura, sia stato incontrato il record endfile

su un file esterno o sia stato fatto un tentativo di leggere oltre la fine di un fileinterno per il secondo.

Si ricordi che, come già sopra accennato, una condizione di errore può essereprovocata da vari eventi fra i quali un disaccordo in tipo fra l'elemento della lista

di I/O ed il descrittore ripetibile associato nella specificazione di formato oppure un

errore di conversione dovuto alla presenza nel campo di ingresso di un carattere

non valido, oppure un disaccordo fra le caratteristiche assunte per il file associato

all'unità presente nella lista di controllo e quelle effettivamente dichiarate nellafrase OPEN per quell'unità.

0'! Inoltre, se durante un 'operazione di lettura si verifica una condizione di fine/I file o di errore, i valori degli elementi della lista di ingresso diventano indefiniti. A

Infine, se nella lista di controllo non è presente né lo specificatore 10STAT

né END né ERR e si verifica una condizione di errore o fine file, ciò provoca una

condizione d'errore per il programma la cui esecuzione, secondo il FORTRAN77, deve cessare.

L'ultimo specificatore, REC = n, dove n è un'espressione intera, riguarda le

operazioni di I/O su files ad accesso diretto che verranno illustrate nel § 18.6.

18.4. Connessione di un file esterno: frasi OPEN e CLOSE

Per poter fare riferimento in una frase di I/O ad un file esterno occorre che

questo sia «conosciuto dal programma», ossia connesso o associato ad una data

unità. I files relativi alle unità di I/O standard sono sempre connessi per tutti i

possibili programmi; essi si dicono pertanto files preconnessi e la dichiarazione

di connessione che vedremo è per essi implicitamente sempre assunta.

Alcuni sistemi prevedono anche la possibilità di preconnettere un file, ad esem­

pio alla stampante o al lettore di schede etc., tramite opportuni comandi rivolti

allinker.

Frase OPEN

Con una dichiarazione di connessione rendiamo accessibile ad un programma

un file che già esiste su qualche supporto esterno, dichiarandone le caratteristiche

e potendo così leggerlo o modificarlo. Si pensi, ad esempio, ad un file esistente

relativo agli stipendi degli impiegati di una ditta. Esso sarà memorizzato su un

disco magnetico e conosciuto all'interno del sistema con un nome, poniamo

STIPENDI. Se vogliamo aggiornare tale file dobbiamo renderlo accessibile da par­

te del programma di aggiornamento e ciò viene appunto fatto connettendo tale

file, identificato dal suo nome, ad una certa unità di I/O rappresentata dall'oppor­

tuno valore intero.

Se, d'altra parte, il file non esiste esso può venire creato dandogli un nome e de­

finendolo con opportune operazioni di scrittura; questo file potrà poi essere me­

morizzato permanentemente, su qualche supporto esterno a seconda delle speci­

fiche date al riguardo.

In ogni caso. per tutti i files che non siano preconnessi occorre che essi sianoesplicitamente connessi tramite l'uso della frase OPEN che ha la seguente forma:

READ (1,50, ERR = 100, END = 200) A, B, CCONTINUAZIONE DELLA NORMALE ELABORAZIONEc

i

'II

i I

IlIi

~ II

r

GOT060C CONDIZIONE D'ERRORE

100

GO TO 60C FINE DEL FILE

200

60 STOP50 FORMAT (3E13.6)

END

OPEN (olista)

dove:

• OPEN è la parola chiave che identifica la frase;

• olista è una lista composta da tutti o parte dei seguenti specificatori separati

da virgole:

Page 184: Fortran

I 1l'·t

I

STATUS = st

Con lo specificatore di stato

STAMPA SUL MEZZO PRN.

WRlTE (2, 'C'v STAMPAvSULvMEZZOvPRN")'}

associa il file (stampante) PRN all'unità 2, così la successiva istruzione

OPEN (UNlT = 2, FILE = 'PRN')

file identificato, può essere diverso per ogni esecuzione del programma in cui leistruzioni sopra riportate compaiono: le istruzioni di I/O che nel corso di quel

programma si riferiscono all'unità 6 comportano così operazioni di I/O sul file

individuato dal valore attuale di NOMEFI.

361

produce sulla stampante, la linea

dove:• st è una espressione di tipo carattere che deve valere una delle seguenti strin­ghe: 'OLD', 'NEW', 'SCRATCH' o 'UNKNOWN', stabiliamo certe caratteristiche

sulla vita del file il cui nome è presente nella stessa frase OPEN.Se st vale 'OLD' allora il file deve già esistere, mentre se vale 'NEW' esso non

deve preesistere. Se un file con specifica 'NEW' viene connesso, allora il suo stato

viene mutato in 'OLD' così che ogni successivo tentativo di riconnettere quel

file con STATUS uguale a 'NEW' fallisce, ciò per evitare eventuali modifiche ac­

cidentali di un file già esistente. Se st vale 'SCRATCH' si ha la creazione di un

file speciale di esclusivo uso da parte del programma, la sua durata è quella del­

l'esecuzione del programma: quando l'esecuzione del programma termina anche

il file cessa di esistere. Evidentemente, se la dichiarazione del file prevede lo spe­cificatore FILE, il file non può essere di tipo SCRATCH. Se st vale 'UNKNOWN'o se lo specificatore di stato è omesso, lo stato del file dipende dal sistema: gene­ralmente, se il file già esiste, lo stato assunto è 'OLD', altrimenti è 'NEW'.

Esempio 18.6. Scrittura sulla stampante. Supponiamo che nel sistema di calcolo

in uso la stampante sia identificata dal nome PRN. La seguente istruzione

CHARACTER • 8 NOMEFIREAD '(A)', NOMEFIOPEN (UNIT =6, FILE = NOMEFI)

FILE = 'PRN', FILE = 'CON', FILE = 'STIPENDI'

FILE = 'A:VAL.DAT'

dove n è un'espressione di tipo carattere, ad esempio possiamo avere:

FILE = n

UNIT = u

FILE = nSTATUS = stACCESS = ace

FORM = formRECL = 2BLANK = bi

ERR = s10STAT = v

Esempio 18.5. Uso di un nome variabile di file

Il primo specificatore, UNIT = u o semplicemente u, deve essere sempre

presente, mentre gli altri sono facoltativi. In questo specificatore, u ha la forma

già illustrata nel § 18.3.

Il file che deve essere associato all'unità u deve avere, se già esiste, un nome che

sia conosciuto dal sistema, ad esempio il nome che tale file ha se memorizzato

su nastro o disco, oppure il nome che il sistema dà ai files che rappresentano i

comuni mezzi di I/O, quali la stampante o la telescrivente, come PRN, LPT o

CON e simili. Tale nome è quello che deve comparire nello specificatore

360

Le espressioni, in questo caso costanti, 'PRN', 'CON', 'STIPENDI' e

,A : VAL.DAT' sono possibili nomi di files riconoscibili dall'attuale sistema di

'Icalcolo. Per quanto riguarda i nomi dati dal sistema ai comuni mezzi di I/O e

l/I 1, la forma corretta per i nomi di files sui vari supporti magnetici occorrerà il~''l' consultare il relativo manuale del sistema. Oltre a nomi costanti di files si possono' I

usare anche nomi variabili, come mostra il seguente esempio.

Con queste istruzioni viene letta, dal mezzo standard di ingresso, una stringa

di caratteri e assegnata alla variabile carattere NOMEFl che, nella successiva frase

OPEN, costituisce il nome del file associato all'unità 6. Tale nome, e quindi il

Esempio 18.7. Connessione del file esistente, 'A: VAL.DAT', all'unità 6, con

una delle successive istruzioni OPEN equivalenti:

OPEN (6, FILE = 'A:VAL.DAT', STATUS = 'OLD')OPEN (6, FILE = 'A:VAL.DAT', STATUS = 'UNKNOWN')OPEN (6, FILE = 'A:VAL.DAT').

d

Page 185: Fortran

II

~!

I

I

362

Lo specificatore

ACCESS = ace

dove:

• ace è un'espressione carattere che deve valere 'SEQUENTIAL' o 'DIRECT'

dichiara il modo di accesso al file. Con 'SEQUENTIAL' il modo di accesso è se­

quenziale, con 'maser è invece diretto; nel § 18.6 verranno illustrate le carat­teristiche e l'uso dei files ad accesso diretto. Se lo specificatore ACCESS è omesso

_vie~ne assunto il modo sequenziale: i files -connessi con le istruzioni OPEN dagliesempi precedenti sono allora tutti ad accesso sequenziale.

Già abbiamo illustrato la possibilità di usare records con e senza formato.

Un file può essere costituito da records tutti con formato o tutti senza formatoin accordo con lo specificatore

FORM = form

dove:

• form è un'espressione carattere che deve valere 'FORMATTED' o'UNFORMATTED', rispettivamente per files con e senza formato.

~I

~_t~edficatore è omesso iLfìle è considerato dal sistema con formato '(ryr; I se l'accesso è .sequeneiale, ma senza formato se l'accesso è diretto. Alloratlì"ill li: ,iV

!i files degli esempi precedenti sono costituiti da~eooids~conToimato e ad ac;ces~-L1JI·1 so sequenziale. p

- ---Ili

Esempio 18-8- Connessione di un file sequenziale con formato di tipo SCRATCHall'unità I:

OPEN (I, STATUS = 'SCRATCH', ACCESS = 'SEQUENTIAL',• FORM = 'FORMATTED').

Quando un file sia stato dichiarato ad accesso diretto è necessario stabilire apriori la lunghezza, costante, dei suoi records, misurata in caratteri per i records

con formato o in base all'unità di misura adottata dal sistema per quelli senza for­mato. Tale dichiarazione viene fatta tramite lospecificatore

RECL = ~

dove:

• ~ è un'espressione intera il cui valore dà l'opportuna informazione sulla lun­ghezza.

f\I\J Si noti che tale specificatore non deve essere presente se il file è stato dichiarato" r~ ad accesso sequenziale. [,J \

1363

Esempio 18.9. Si considerino le seguenti frasi:

OPEN (6, FILE = 'A:DIR.DAT', ACCESS = 'DIRECT', STATUS = 'OLD',*RECL = 8)

OPEN (7, FILE = 'C:VAL.FM', ACCESS = 'DIRECT', STATUS = 'NEW',*FORM = 'FORMATTED', RECL = 8) -

La prima associa all'unità 6 il file identificato dal nome A :DIR.DAT, già esi­

stente e memorizzato su un supporto magnetico. Le sue caratteristiche sono di

essere: ad accesso diretto con records senza formato (il dichiaratore FORM è

infatti assente e l'accesso è diretto); la lunghezza di ciascun record è 8 unità.

La seconda frase OPEN associa all'unità 7 il file che verrà creato con il nomeC:VAL.FM. Le sue caratteristiche sono di essere: ad accesso diretto con records

con formato di lunghezza 8 caratteri ciascuno.

Nella definizione delle caratteristiche di un file costituito da records con for­

mato, possiamo stabilire il modo di interpretare i caratteri blank all'interno di

campi numerici: ignorarli o considerarli come cifre zero. A questo scopo esistelo specificatore

BLANK = bI

dove:

• bI è un'espressione carattere che deve valere 'NULL' o 'ZERO' a seconda se

vogliamo ignorare o considerare come zero i caratteri blanks nei campi numerici,

tenendo conta.checomunque un campo composto da tutti blanks è considerato

contenere il valore zero.

Se tale specificatore è omesso, viene assunta l'opzione 'NULL'. Ricordiamo

inoltre che tale scelta può essere ulteriormente, di volta in volta, cambiata con

l'uso dell'apposito descrittore non ripetibile BN o BZ all'interno di una specifi­

cazione di formato (cfr. cap. 13LL~~ec_i!icatore BLANK infine, non deve essere

presente se il file è costituito da records senza formato.- ---"- - -- ._- ----

Il trattamento delle condizioni di errore che si possono verificare durante la

connessione di un file è stabilito con gli ultimi due specificatori ERR e IOST AT.

Una condizione d'errore si potrebbe presentare nel caso in cui un file dichiarato

come 'OLD' non esista o se il tipo del file esistente non si accorda con quello sta­bilito da certi specificatori.

Ricordiamo che in queste circostanze. se nessuno dei due specificatori ERR oIOST AT è presente si ha un arresto dell'esecuzione del programma.

Con lo specificatore

ERR =s

/ ,

Page 186: Fortran

364

dove:

• s è l'etichetta di una frase appartenente alla medesima unità di programmasi stabilisce che in caso di errore l'esecuzione riprenda a partire dalla frase di eti­

chetta s.

Se è presente lo specificatore:

IOSTAT = v

dove:

• v è un nome di variabile o elemento di variabile dimensionata di tipo intero,

allora in relazione al verificarsi o meno di errori v assume i seguenti valori:

• zero se nessun errore è avvenuto;• un valore positivo dipendente dal sistema in caso contrario.

La variabile v può essere controllata per avere informazioni sull'esito dell'o­

perazione di connessione.

(vJ Tenendo presente la re~.ola generale. che una unità non Pliò ~sse~e _co~~:~so:,'contemporaneamente a ptu files, possiamo avere una corretta connessione neil{

casi seguenti:

a) se il file nella OPEN è diverso da quello già connesso, allora il file preceden­

te viene sconnesso (vedi frase CLOSE più avanti) ed il nuovo file viene connesso'b) se il file nella OPEN è il medesimo, ossia già connesso, oppure se l'unità

indicata è una di quelle preconnesse, allora l'unico specificatore consentito è il

BLANK per stabilire esplicitamente l'interpretazione dei blanks.

I, Il In ogni caso è P!~ibito tentare d~ _~~n.!!~!.ereu~y-nit4a~ un file che sia già /',' \,, \ \ associato ad un 'altra unità. -- - I

Frase CLOSE

Al termine dell'esecuzione di un programma ogni file che sia stato connesso

viene automaticamente sconnesso o chiuso.Se vogliamo operare tale sconnessione prima della fine del programma perché

desideriamo ad esempio riconnettere quel file ad altra unità, possiamo usare la

frase

CWSE (cllista)

dove:• cllista è una lista composta da uno o più dei seguenti specificatori separatida virgole:

365

u

UNIT = u

STATUS = st

ERR = sIOSTAT = v

Lo specificatore u oppure UNIT = u deve essere sempre presente. Gli speci­

fica tori u, UNIT, ERR e IOSTAT hanno il medesimo significato visto nella frase

OPEN.Con lo specificatore

STATUS = st

dove:• st è un'espressione carattere che deve valere 'KEEP' o 'DELETE', si danno

indicazioni sulla possibilità o meno di riconnettere il file durante l'esecuzione

del programma. Se st vale 'KEEP' il file che era connesso all'unità u può essere

successivamente connesso alla medesima o altra unità; se invece st vale 'DELETE',

il file connesso all'unità u cessa di esistere: ciò significa che il file non può essere

ulteriormente connesso durante l'esecuzione del programma e non vuoI dire che

il file deve essere cancellato dalla memoria ausiliaria sulla quale è memorizzato.

Se lo specificatore STATUS è omesso, viene automaticamente assunta la di­

chiarazione KEEP a meno che il file in questione non sia stato connesso con la

specifica STATUS = 'SCRATCH', nel qual caso viene assunta la dichiarazione

DELETE.Ricordiamo infine che le frasi OPEN e CLOSE non esistevano in F66.

Esempio 18.10. Le seguenti frasi

OPEN (6, FILE = 'C:VAL.DAT', STATUS = 'OLD')

CLOSE (6, STATUS ='KEEP')

OPEN (7, FILE ='C:VAL.DAT')

implicano la connessione del file CVAL.DAT all'unità 6, quindi la sconnessione

da quella unità e la successiva riconnessione di quel file all'unità 7.

18.5. Frasi di posizionamento: BACKSPACE e REWIND

Può essere utile poter esplicitamente posizionare la testina di lettura/scrittura

di un mezzo magnetico su di un record voluto di un file sequenziale.

I

Ii i

t

IIl

I,,

1-1 I

n\,

I

Page 187: Fortran

366 367

A tale scopo esistono le frasi

BACKSPACE u oppure BACKSPACE (auxlista)

e

REWIND u oppure REWIND (auxlista)

tutti i records successivi.Le istruzioni BACKSPACE e REWIND vengono usate di solito solo per leggere

i records di un file. Vedremo comunque che i files ad accesso diretto consentonoun aggiornamento dei loro records nel senso che è possibile modificare un certo

record lasciando inalterati tutti i precedenti ed i successivi.

Si osservino le tre frasi

esse realizzano in modo assai semplice il posizionamento sul record endfile del fileESPER.DAT. La frase READ non contiene alcuna lista, ma la sua esecuzione,

5 READ (8, END = lO)GOTOS

lO BACKSPACE 8

PROGRAM AGGESPDICHIARAZIONIREAL TEMPINTEGER DATA (3), ORA (3)LETTURA DATI DAL MEZZO STANDARD D'INGRESSO

READ., TEMP, DATA, ORAIL FILE ESPER. DAT E' ASSOCIATO ALL'UNIT A' 8OPEN (8, FILE = 'ESPER.DAT', STATUS = 'O~D', FORM =

.'UNFORMATTED', ACCESS = 'SEQUENTIAL )POSIZIONAMENTO SUL RECORD ENDFILE

5 READ (8, END = lO)GOTOS

lO BACKSPACE 8I DATI LETTI VENGONO SCRITTI COME ULTIMO RECORDDEL FILE AL POSTO DI ENDFILE, CHE VIENE ULTERIORMENTE

AGGIUNTO AL FILEWRITE (8), TEMP, DATA, ORAENDFILE 8STOPEND

CCC

C

C

C

c

Esempio J8. J2. Si vuole aggiornare un file di nome ESPER.DAT, i cui .recordscontengono i valori: temperatura, data ed ora relativi ad un certo espenmento.Tali records sono senza formato ed il file è ad accesso sequenziale, vogliamo infat­ti solo aggiungere alla fine del file il record relativo all'ultima rilevazione fatta,

l'ultimo record del file è il record end file.Un semplice programma per realizzare quanto sopra detto, dovrà contenere le

specifiche del file in una opportuna frase OPEN, dovrà prevedere la lettura dei

dati che devono essere aggiunti al file. Siano questi TEMP per temperatura,

DATA (3) il vettore di 3 componenti per giorno mese ed anno ed il vettore

ORA (3) di 3 componenti per ora, minuti e secondi.

WRITE (2, '(lOE13.6)') VBACKSPACE 2

Esempio J8. JJ. Le seguenti frasi

fanno si che venga scritto sul file SEQ un record e successivamente provocano il

posizionamento della testina all'inizio del record appena scritto.

REAL V(lO)OPEN (UNIT = 2, FILE = 'SEQ', ACCESS = 'SEQUENTIAL')

dove:

• u è l'identificatore di unità come già precedentemente illustrato;

• auxlista è la lista di specificatori UNIT, ERR e 10STAT già illustrati nel

§ 18.2, in cui lo specificatore UNIT deve necessariamente essere presente.

L'esecuzione di BACKSPACE fa si che la testina si posizioni all'inizio delrecord appena trasmesso; ciò consente, ad esempio, di rileggere un record appena

letto.

Si noti che all'inizio dell'esecuzione di un programma, per ogni file connesso,

il record che sta per essere letto è il primo. Ovviamente, eseguendo più volte una

BACKSPACE è possibile il posizionamento su un record precedente.Se, d'altra parte, desideriamo ritornare all'inizio del file è conveniente l'uso

della REWIND, che causa appunto il posizionamento sul primo record del fileassociato ad u nella REWIND stessa.

f r L'uso di tali frasi è particolarmente utile in connessione con l'uso del record

\ l' !endfile. Quando un tale record sia stato letto o scritto, nessuna ulteriore opera­\ zione di I/O può essere effettuata sul file in questione senza prima aver eseguito

una frase BACKSPACE o REWIND.

IOccorre mettere in evidenza una importante caratteristica dei files ad accesso

r sequenziale. Quando un record viene scritto su di un file sequenziale, esso è l'ul­\ I, timo record del file, COSI' ogni eventuale altro record su~~essivo presente sul file, vtene distrutto. Non possiamo allora usare le frasi BACKSPACE e REWIND per

\ \ I posizionarsi su un certo record, riscriverci sopra una nuova versione lasciando irecord successivi inalterati: lascrittura del nuovo record è possibile solo perdendo'

Page 188: Fortran

368

18.6. Files ad accesso diretto

Abbiamo già messo in luce il fatto che usando come memoria ausiliaria il disco

magnetico, che può essere disco rigido o fisso o dischetto (floppy disk), riusciamo

ad ottenere da una parte prestazioni, riguardo ai tempi d'accesso, molto miglion

rispetto ai nastri e dall'altra la possibilità di accedere ai records di un file, se ilmodo d'accesso è DIRECT, in modo non sequenziale ma stabilito in base al nu­

mero d'ordine del record voluto. Tale possibilità di accesso diretto, detto anchecasuale, è data dalla struttura fisica del mezzo che riportiamo in fig. 18.1.

j.

\

~:

Ii

369

RECL =2

come già illustrato nel § 18.4.

dove n è un'espressione intera.

Ricordiamo che per dichiarare un file ad accesso diretto, dobbiamo includere

nella frase OPEN lo specificatore

ACCESS = 'DIRECT'

e dobbiamo altresì dichiarare la lunghezza di ciascun record del file con lo spe­

cificatore

binazione del movimento orizzontale «avanti-indietro» della testina e di quello

di rotazione del disco, consente il posizionamento della testina in qualsiasi punto

di qualsiasi traccia. Ovviamente il tempo massimo richiesto per accedere ad unrecord è quello necessario per lo spostamento della testina dalla traccia più in­

terna a quella più esterna, o viceversa, più quello per un giro completo del disco.

Le caratteristiche di velocità d'accesso del disco lo hanno fatto di gran lunga

preferire al nastro per quasi tutte le applicazioni, tanto che oggi il sistema operati­vo di un elaboratore è basato proprio sul disco, si pensi ad esempio alla categoria

dei sistemi DOS (Disk Operating System).Il fatto che il disco consenta l'accesso diretto ai records di un file non implica

che necessariamente tutti i files su di esso memorizzati siano ad accesso diretto;come è già stato osservato, possono essere definiti sul disco anche files ad acces­

so sequenziale.I files ad accesso diretto risultano particolarmente utili in determinate circo­

stanze: quando si voglia leggere un record senza dover necessariamente scorrere

tutti i precedenti o quando si voglia riscrivere su di un record una nuova versione

senza perdere i records successivi.Per accedere ad un record su di un file ad accesso diretto, occorre conoscere

il numero d'ordine, in quanto tutti i records di un file sono ordinati. Il numero

d'ordine del record interessato all'operazione di I/O deve essere specificato nella

lista di controllo della frase di I/O mediante lo specificatore

REC=n

Testina dilettura/scritturaTraccia

provocando comunque la lettura di un record, i cui valori non sono assegnati ad

alcuna variabile, genera uno «scorrimento» del file che viene ripetuto per effettodella frase GOTO 5 finché non viene letto il record endfile. A questo punto lo

specificatore END = lO provoca il salto alla frase lO BACKSPACE 8 la qualeposiziona la testina sul record appena letto ovvero sul record endfile. La succes­

siva frase WRITE provoca la sostituzione del record endfile con quello senza for­

mato, costituito dai sette valori di TEMP, DATA e ORA. La successiva frase

ENDFlLE 8 scrive il nuovo record endfile. La fine dell'esecuzione del programma

comporta quindi l'automatica sconnessione del file come se fosse eseguita una

frase CLOSE (8).

Figura 18.1. Struttura dell'unità disco magnetico.

L'unità disco magnetico è infatti costituita da un disco, le cui facce sono ri­

coperte da materiale magnetico, che ruota intorno ad un asse verticale; sul disco

si muove orizzontalmente una testina di lettura/scrittura.L'informazione è memorizzata su tracce concentriche, di modo che la com-

Esempio 18.13. Si considerino le seguenti frasi:

OPEN (7. FILE = 'ACCDIR', ACCESS = 'DI RECT' ,*FORM = 'UNFORMATTED', RECL = 12)

WRITE (7, REC = 2) X, Y, Z

READ (7, REC = 2) A, B, C

Page 189: Fortran

370

La prima frase dichiara le seguenti caratteristiche del file di nome'ACCDIR'associato all'unità 7: esso è ad accesso diretto e i suoi records senza formato sonolunghi 12 unità.

La seconda scrive come secondo record del file 'ACCDIR' un record (di lun­ghezza 12) composto dai 3 valori di X, Y e Z rispettivamente. La terza causa

la lettura del 20 record del file 'ACCDIR' e definisce le variabili A, B, C con i va­lori, senza alcuna conversione, di X, Y, e Z precedentemente scritti.

Esempio 18.14. II seguente programma:

PROGRAM MEDVALREAL MEDIADIMENSION A(20), MEDIA (50)

C CONNESSIONE DEL FILE 'VALORI' ALL'UNITA' 2

OPEN (UNIT = 2, FILE = 'VALORI', ACCESS = 'DIRECT', RECL = 80,*STATUS = 'OLD')

C LETTURA DEI VALORI DI M E N, CON M MINORE O UGUALE A 20C E N MINORE O UGUALE A 50 (NUMERO TOTALE DEI RECORDSC PRESENTI NEL FILE 'VALORI')

READ *,M,N

C DEFINIZIONE DEL VETTORE A E DEL VETTORE MEDIA,C TRAMITE LA LETTURA DI UN RECORD PER VOLTA DAL FILE

DOSI=I,NREAD (2, REC = I) (A(J), J = 1, M)MEDIA (I) = O.D04K=I,MMEDIA (I) = MEDIA (I) + A(K)

4 CONTINUEMEDIA (I) = MEDIA (I)/MCONTINUE

C STAMPA SULLA STAMPANTE 'PRN' DEL VETTORE MEDIA,C IL FILE 'PRN' VIENE ASSOCIATO ALL'UNITA' 3

OPEN (3, FILE = 'PRN')WRITE (3, 6) MEDIASTOP

6 FORMAT (IOX, 'VETTORE MEDIA RICAVATO DAL FILE VALORI'/*5 (2X, EI3.6))

END

definisce le prime N componenti del vettore MEDIA. Ciascuna componente è la

media degli M valori letti da ciascuno dei primi N records del file 'VALORI'

associato all'unità 2. Questo file è ad accesso diretto ed è costituito da records

senza formato di lunghezza 80 (= 20 x 4 unità). Esso deve essere stato preceden­temente definito in modo tale da contenere in ciascuno dei primi N records al­

meno M valori. II vettore MEDIA calcolato viene stampato sul file stampante'PRN' di tipo sequenziale costituito da records con formato, associato all'unità3.

371

Abbiamo già notato che la lunghezza dei records, in un file ad accesso diretto,

deve essere sempre la medesima, quella definita nello specificatore RECL.

D'altra parte in F77 è possibile scrivere un record senza formato di lunghezza

inferiore a quella stabilita; in questo caso la parte mancante viene riempita con

valori indefiniti. Ciò è possibile anche con records con formato di un file ad

accesso diretto: in questo caso il record eventualmente più corto viene allungato

con dei caratteri blanks per raggiungere la lunghezza stabilita.

Esiste poi un altro tipo di automatismo nelle operazioni di 110 ad accesso di­

retto con formato: se la specificazione di formato e la lista di 110 sono tali datrasmettere più di un record, allora ogni record trasmesso viene numerato aggiun­gendo una unità al numero d'ordine del record precedente. Così le frasi

OPEN (3, FILE = 'DIRFORM', ACCESS = 'DIRECT',*FORM = 'FORMATTED', RECL = 100)

WRITE (3, 30, REC = l) (A(I), I = 1,20)30 FORMAT (lO GIO.2)

provocano la scrittura, sul file 'DIRFORM', di due records ciascuno costituito

da lOdati rappresentati in accordo al descrittore G l0.2; il primo record ha nu­

mero d'ordine 1 ed il secondo ha numero d'ordine 2. Si noti, infine, che se il file

'DIRFORM' contenesse già il primo ed il secondo record, questi verrebbero sosti­

tuiti da quelli appena scritti.

18.7. Indagine sulle unità di 110e sui files: frase INQUIRE

Può essere utile avere la possibilità di sapere le caratteristiche di files esterni

conosciuti dal sistema eia unità usate in un programma. Ciò può essere ottenutoeseguendo la frase INQUIRE che definisce il valore di variabili el» elementi divariabile dimensionata, in modo tale da sapere se un tile è costituito da records con

formato, se è ad accesso diretto o sequenziale e così via.La frase in questione è la seguente

INQUIRE (i1ista)

dove

• INQUIRE è la parola chiave che identifica la frase;

• ilista è una lista di specificatori, separati da virgole, scelti fra i seguenti:

u

UNIT = u

FILE = nl

ACCESS = ace

FORM = fm

Page 190: Fortran

372373

(( f~

'SEQUENTIAL' o 'DIRECf' se il file è connesso per un accesso sequenziale odiretto, ma resterà indefinita se non c'è alcuna connessione. Analogamente, fmassume il valore 'FORMATIED' o 'UNFORMATTED' a seconda del tipo di con­nessione, ma resta indefinita se non c'è connessione. Ancora, ~ assume come valorela lunghezza dei records del file se questo è connesso con un accesso diretto, al­trimenti resta indefinita; bi assume il valore 'ZERO' o 'NULL' a seconda dei casi,ma resta indefinita se non c'è connessione o se il file è costituito da records senzaformato.

RECL = ~

BLANK = biSEQUENTIAL = seqDIRECf = dirFORMATTED = fmtUNFORMATTED = unfEXIST = ~l

OPENED = ~2

NAMED = ~3

NUMBER=numNAME = n2NEXTREC = nrERR =sIOSTAT = v

Viceversa, gli specifica tori

SEQUENTIAL = seq, DIRECf = dir,UNFORMATTED = unf

FORMATTED = fmt,

. Negli specificatori indicati tutti gli elementi alla destra del segno di uguaglian­za devono essere nomi di variabile o nomi di elementi di variabile dimensionataad eccezione di u e di nl che possono anche essere un'espressione intera e un'e­spressione carattere rispettivamente. In particolare, ace, fm, bi, seq, dir, fmt,unf e n2 sono di tipo carattere; ~ l, ~2 e ~3 sono di tipo logico; ~, num, nr e v sonodi tipo intero e s è un'etichetta di una frase eseguibile appartenente alla medesi­ma unità di programma.

Con questa frase possiamo conoscere le caratteristiche di un file attraverso ilsuo nome anche se non è connesso ad alcuna unità, oppure quelle di un file con­nesso ad una data unità.

1Nel primo caso nella ilista deve essere presente lo specificatore FILE ed as-j

"li sente quello UNIT, nel secondo deve essere presente lo specificatore UNIT e non \'1}quello FILE.

La presenza degli altri specificatori è facoltativa; in generale, l'effetto dell'ese­cuzione di una frase INQUIRE è quello di assegnare dei valori alle entità variabilinegli specificatori. In alcuni casi, però, tale assegnazione può non avvenire e lacorrispondente entità resta indefinita.

Per molti versi gli specificatori della INQUIRE sono simili a quelli della OPEN,però con un effetto diverso.

Così gli specifica tori l(

ACCESS = ace, FORM = fm, RECL =~, BLANK = bi

fanno sì che ace, fm, ~ e bi diventino o meno definite: ace assumerà il valore

'. . consentono di conoscere le corrispondenti caratteristiche di un file anche se'\' questo non è connesso. 11 '

In ogni caso seq, dir, fmt e unf vengono definite con i valori 'VES' 'NO' o'UNKNOWN'. '

Così seq assume il valore 'VES' se il file consente l'accesso sequenziale, 'NO' senon lo consente e 'UNKNOWN' se da parte del sistema non è possibile determi­nare questa caratteristica. Per gli altri tre specificatori e relativi elementi dir, fmte unf valgono le stesse considerazioni fatte per lo specificatore SEQUENTIAL.

Con l'uso degli specifica tori

EXIST =~l, OPENED =~2, NAMED =B

~l, ~2, ~3 assumono un valore logico, .TRUE. o .FALSE.. a seconda del verifi­carsi o meno della corrispondente condizione. Con EXIST viene effettuato ilcontrollo se il file specificato o l'unità specificata esiste. Con OPENED, ~2 risultavera se il file specificato è connesso a qualche unità, o se l'unità specificata è con­nessa a qualche file, falsa altrimenti. Con lo specificatore NAMED, ~3 assume il

valore vero se il file connesso ha un nome, falso altrimenti.

Gli specificatori

NUMBER = num, NAME = n2

definiscono num e n2 rispettivamente con il numero dell'unità attualmente con-

~.

\l

i

. ~ .rs1tm--------- .....

Page 191: Fortran

374

nessa al file specificato e con il nome del file attualmente connesso all'unità spe­

cificata. Se non c'è alcuna unità connessa al file num resta indefinita; altrettanto

n2 resta indefinita se il file connesso all'unità non ha un nome.

Riguardo ancora allo specificatore NAME c'è da notare che se esso appare inuna frase INQUIRE in cui figura lo specificatore FILE, il valore assunto da

n2 può non essere uguale a quello riportato nello specificatore FILE; ad esem­

pio il valore di n2 può contenere anche una sigla di identificazione relativa all'u­

tente. Se poi nessun file è connesso all'unità specificata n2 rimane indefinita.

375

Esempio 18.15. Si considerino le seguenti frasi

LOGICAL LOG

INQUIRE (FILE = 'V A.L.DAT', OPENED = LOG, NUMBER = NUM)

IF (LOG) THENC IL FILE VAL.DAT E' GIA' CONNESSO ALL'UNITA' NUM

WRITE (NUM) A, B, C

ElSEIL FILE VAL.DAT NON E' CONNESSO AD ALCUNA UNITA',ESSO VIENE ALLORA ASSOCIATO ALL'UNITA' 3

OPEN (3, FILE = 'VAL.DAT') r t r ( (C /1 l Cfltlr 1( e

Lo specificatore

NEXTREC = or

causa la definizione di or con il valore m + l dove m è il numero d'ordine dell'ul­

timo record trasmesso da o verso il file se questo è ad accesso diretto; se nessun

record è stato trasmesso allora nr assume il valore 1. Se invece il file non è ad

accesso diretto o se è avvenuto un errore durante la trasmissione tale da rendere

indefinita la posizione richiesta, or resta indefinita.

CC

WRITE (3) A, B, C

ENDIF

:::, ( y , \ l" \4 ~ ( (I ( A I C (, 1(1 f C

Lo specificatore

IOSTAT = v

definisce v con il valore zero se non esiste alcuna condizione d'errore relativa al

file o all'unità specificata nella INQUIRE, oppure con un numero positivo, dipen­

dente dal sistema, se, al contrario, esiste una condizione d'errore.

Lo specificatore

ERR=s

ha il medesimo significato illustrato nel § 18.4.

Una variabile o elemento di variabile dimensionata che figura in uno degli spe­

cificatori della frase INQUIRE non può essere presente in nessun altro specifica­

tore della medesima frase INQUIRE; tale divieto si estende anche a tutte le entità

che in qualche modo sono associate, ad esempio tramite la frase EQUIVALENCE,

a quella variabile o elemento di variabile dimensionata.

Notiamo infine che la frase INQUIRE non esiste in F66.

Con la frase INQUIRE siamo in grado di sapere se il file VAL.DAT è connesso

o meno e in caso affermativo a quale unità. Se il file è già connesso LOG assume

il valore vero e NUM il valore intero che identifica l'unità a cui il file è connesso.

Con la struttura IF successiva, in base al valore assunto da LOG si possono com­

piere operazioni di 110 sull'unità NUM se LOG è vera oppure in caso contrario il

file VAL.DAT viene connesso all'unità 3 tramite la quale si compiono ancora

operazioni di 110 sul file.

18.8. Files interni

Un file interno può essere considerato come una zona di memoria di transito,

utile per dei trasferimenti, con eventuali conversioni, di dati da una parte all'altra

della memoria entrambe interne.Un file interno è una delle seguenti entità di tipo carattere: una variabile, un

elemento di variabile dimensionata, una sottostringa o una variabile dimensionata.

Se un tale file è una variabile o elemento di variabile dimensionata o una sotto­

stringa allora è costituito da un solo record, mentre se è una variabile dimensio­

nata esso è costituito da tanti records Quanti sono gli elementi della variabile.Qualunque operazione di I/O su di un file interno inizia sempre dal primo record

del file.II riferimento al file avviene direttamente nella frase di 110usando il suo nome

come identificatore della unità di I/O. Tali operazioni devono essere di tipo

Page 192: Fortran

376

sequenziaie sotto il controllo esplicito di formato.Una entità usata come file interno può essere definita oltre che con una

operazione di scrittura, anche, ad esempio, tramite una operazione di lettura da

un'altra unità, o con operazioni di assegnazione di tipo carattere.Se durante un'operazione di scnttura su di un file interno viene prodotto un

record di lunghezza inferiore a quella specificata per il file il record prodotto vieneallungato con l'aggiunta alla sua destra di caratteri blank.

Tale tipo di file non esisteva in F66, nè quindi le corrispondenti operazioni

di I/O.

Esempio 18.16. Un file di nome ACCDIR ad accesso diretto contiene 25 records

con formato. Ciascun record è costituito da 4 campi contenenti dei numeri scritti

secondo il descrittore EI5.7, seguiti da un ultimo campo costituito da un valorelogico rappresentato secondo il descrittore LI. In totale quindi la lunghezza,in caratteri, di ciascun record è 61.

Siano N, O:s;;; N:S;;; 25, i records contenenti il valore vero nell'ultimo campo. Vo­gliamo definire le prime N righe di una matrice reale, RMAT, in modo tale che es­se siano nell'ordine i 4 valori reali dei records che contengono nell'ultimo campo

il valore vero.

Possiamo far uso della variabile carattere TRANS di lunghezza 60 come file

interno in cui leggere i records di ACCDIR ed usarla poi come unità di ingresso

per definire, se è il caso, la riga opportuna di RMAT. Il seguente programma rea­

lizza quanto sopra richiesto.

PROGRAM FIUNTLOGICAL L61CHARACTER * 60 TRANSREAL RMAT (25, 4)

C IL FILE 'ACCDlR' E' ASSOCIATO ALL'UNITA' 3C LE CARATTERISTICHE DI QUESTO FILE SONO DATE NELLA OPEN

OPEN (UNIT = 3, FILE = 'ACCDIR', FORM = 'FORMATTED', RECL =*61, ACCESS = 'DIRECT',STATUS = 'OLD')

IR = lDO 20 I = 1,25READ (2, 3, REC = I) TRANS, L61IF (L6l) THENREAD (TRANS, FMT = 4) (RMAT (IR, J), J = 1,4)IR = IR + lENDIF

20 CONTINUEIF (IR.EQ.l) THEN

PRINT *, 'NESSUN RECORD DI ACCDlR CONTIENE IL',*'vALORE VERO, RMAT NON Eli STATA DEFINITA'

zd

377

ELSEPRINT *, 'SONO STATE DEFINITE LE PRIME', IR - l,

*'RIGHE DI RMAT, NEL MODO SEGUENTE:'WRITE (*, 5) «RMAT (I, J), J = 1,4), I = l, IR - l)

END IFSTOP

3 FORMAT (A60, Ll)4 FORMAT (4E15.7)5 FORMAT (4 (IX, EI5.7»

END

Esempio 18.17. Vogliamo scrivere, usando un file interno, le opportune frasi

di l/O che permettano di arrotondare il valore di ciascuna componente Vi' l :s;;; i :s;;;100, di un vettore reale v precedentemente definito, a due cifre decimali, sup­

ponendo che - 1000 :s;;; v; :s;;; 10000 per ogni i.

CHARACTER * 8 ARROT2 (IOO)DIMENSION VET (100)

c USO DEL VETTORE ARROTI COME FILE INTERNO, SULC QUALE VENGONO SCRITTI GLI ELEMENTI DI VETC CIASCUNO SECONDO IL DESCRITTORE F8.2

WRITE (ARROTI, '(F8.2)') VETC I VALORI ARROTONDA TI GIA' SCRITTI IN ARROT2C VENGONO RILETTI IN VET

READ (ARROn, '(F8.2)') VETC USO DI VET

Il file interno ARROT2 (100) viene definito, scrivendoci i valori di VET

tramite F8.2 che opera il voluto arrotondamento. Tali valori arrotondati vengono

poi riletti dal file ARROT2 per ridefinire VET. In entrambe le operazioni di

scrittura e lettura vengono scritti e letti esattamente 100 records sul e dal file

ARROT2.

Esercizi.

18.1 Scrivere le opportune frasi OPEN e WRITE per stampare dei dati su un file

chiamato LPT di tipo sequenziale costituito da records con formato.

18.2 Scrivere le frasi OPEN e REA D per definire la matrice A di lO righe e IOcolonne, leggendo i valori dei suoi elementi da un file di nome FIL.DATcomposto di records senza formato, di lunghezza 80 bytes (un valore è

rappresentato da 4 bytes), ad accesso diretto.

II!

f~j

l'Ii

Page 193: Fortran

378

18.3 Come l'esercizio 2, supponendo però il file ad accesso sequenziale.

18.4 Scrivere le frasi OPEN e READ per leggere i valori degli elementi di un

vettore VET di lunghezza 100 da un file chiamato PERIF, ad accesso di­

retto con records con formato di lunghezza 20 caratteri. Ciascun recordcontiene 4 campi scritti secondo il descrittore FS.I. Il numero dei records

di PERIF può essere inferiore a 100, comunque l'ultimo record è il recordendfile che, se letto, provoca un salto ad una frase WRITE che scrive ilnumero dei records letti.

18.5 In una classe composta da n (~ 50) studenti vengono fatte mensilmentedelle prove scritte, una per materia, relative a 3 materie indicate con MAT l,MAT2 e MAT3. Scrivere:

a) un programma che aggiorni ogni mese, riportando i voti per ciascun

alunno, un file chiamato PROSCR, tenendo conto che il numero totale

dei mesi è 9. Gli alunni sono venti;

b) un programma che al termine delle prove fornisca le medie per alunno

relative a ciascuna materia.

c) un programma che fornisca l'elenco degli studenti che hanno conseguito

per ciascuna materia un voto medio maggiore o uguale a 6.

Esaminare le varie possibilità esistenti circa la strutturazione del file

PROSCR: sequenziale con e senza formato, ad accesso diretto con e senza

formato.

18.6 Trovare tutte le caratteristiche di un dato elenco di files.

18.7 Scrivere un sottoprogramma FUNCTION che realizzi l'arrotondamento di

un assegnato numero reale r ad un dato numero n di cifre significative. Ci

si deve servire di un file interno nella forma di variabile di tipo carattere dilunghezza 20. Si ottiene il voluto arrotondamento scrivendo il dato con ildescrittore Ew.n, con w opportuno.

4

APPENDICI

Page 194: Fortran

c

Al. Differenze con il subset language

I( subset language presenta, rispetto al fulllanguage F77, le seguenti limitazioni(cfr. [12]):

• I caratteri $ e : non fanno parte dell'alfabeto;

• Non sono ammesse più di 9 linee di continuazione;• Le frasi DATA devono seguire tutte le frasi di specificazione e precedere lefunzioni definite da una frase e le istruzioni eseguibili;

• Non sono permesse linee di commento tra le linee che costituiscono una istru­zione;

• Non sono previsti dati di tipo doppia precisione e complesso;• Una variabile dimensionata non può avere più di tre dimensioni;• Un dichiaratore di dimensione può avere soltanto la forma SUPj;

• Un dichiaratore di dimensione deve essere o una costante o una variabileintera;

• Un'espressione indice può contenere soltanto costanti e variabili intere;• Non sono previsti gli operatori logici .EQV. ed .NEQV.;• Non sono previste le istruzioni: PRINT, CLOSE, INQUIRE, ENTRY,BLOCK DATA, PARAMETER, DOUBLE PRECISION e COMPLEX;• Soltanto nomi di blocchi COMMON possono far parte della lista di una istru­zione SAVE;

• L'istruzione SAVE deve contenere sempre una lista;• Una lista con DO-implicito non può far parte di una istruzione DATA;

• Non sono permesse conversioni di tipo nelle frasi DATA;• La variabile del DO deve essere una variabile intera;

• I parametri del DO devono essere costanti intere oppure variabili intere;• Nell'istruzione GOTO-calcolato l'espressione deve essere una variabile intera;

• Non sono previste istruzioni di I/O guidate dalla lista;• Un identificatore di un file interno deve essere una variabile carattere o un ele­mento di variabile dimensionata carattere;

I •

"

Page 195: Fortran

382

• II numero di unità associato ad un file esterno non deve essere un'espressione;

• Un identificatore di formato deve essere l'etichetta di una frase FORMAToppure una costante carattere;

• Nelle istruzioni di 110 gli specificatori di unità edi formato non includono le

parole chiave UNIT = e FMT = :• Non sono previsti files ad accesso diretto con formato;

• Nelle istruzioni di 110 non è previsto lo specificatore ERR =:• Non sono previste le istruzioni di 110 della forma .READ f, lista-di-ingresso ePRINT f,lista-di-uscita;

• Nelle liste di IlO i parametri del DO-implicito devono essere costanti o variabiliintere. La variabile del DO-implicito deve essere di tipo intero;

• Le costanti, le espressioni ed i nomi di sottostringhe non possono comparirenella lista di uscita;

• L'istruzione OPEN è usata soltanto per specificare l'unità su cui effettuareoperazioni di 110 ad accesso diretto senza formato;

• Non è consentito l'uso di files esterni;• Non sono previsti i seguenti descrittori ripetibili: Iw.m, Dw.d, Gw.d, Gw.dEc;• Non sono previsti i seguenti descrittori non ripetibili: Tn, TLn, TRn, S, SP,SS,: ;

• In una specificazione di formato sono ammesse al più tre coppie di parentesiuna dentro l'altra;

• Non sono previsti «ritorni alternativi»;• Non esistono funzioni intrinseche che prevedono argomenti o risultati di tipodoppia precisione o complesso;

• Non sono previsti nomi generici per le funzioni intrinseche;

• Non sono previste FUNCTION di tipo carattere;• La specificazione della lunghezza di una entità di tipo carattere deve essere

fatta con una costante intera. Non è previsto lo specificatore (*);

• Non sono previste sottostringhe di caratteri;

• Non è prevista l'operazione di concatenazione;

• Non sono previste le funzioni intrinseche LEN, CHAR, INDEX;

• L'associazione di entità carattere effettuata per mezzo di istruzioni COMMONed EQUI VALENCE o attraverso gli argomenti di un sottoprogramma deve avveni­

re tra entità della stessa lunghezza.

Le istruzioni che compongono ciascuna unità di programma devono seguire

l'ordinamento indicato nella seguente figura nella quale le linee orizzontali divi­dono gruppi di istruzioni che non possono .essere mescolate tra loro mentre quelle

verticali delimitano istruzioni che possono essere presenti contemporaneamentein qualsiasi ordine.

383

Istruzione iniziale: PROGRAM, FUNCTION, SUBROtITlNE

Istruzioni IMPLICIT

Altre istruzioni di specificazione

linee di commento Istruzioni FORMAT Istruzioni DATA

Funzioni definite da una frase

Istruzioni eseguibili

Istruzione END

Ordinamento delle i<ltruzionidel Subset Language in una unità di programma.

Page 196: Fortran

AZ. Principali differenzefra il FORTRAN 77 e il FORTRAN 66

Caratteri dell'alfabeto

• In F66 non esistono il carattere apice e il carattere due punti.

385

Espressioni aritmetiche

• In F66 le uniche espressioni miste consentite sono quelle tra operandi di tipo

reale e doppia precisione e tra operandi di tipo reale e complesso.

Espressioni logiche

• In F66 non esistono gli operatori .EQV. e .NEQV.

Espressioni carattere

• In F66 non sono previste espressioni di questo tipo.

Assegnazione aritmetica

• Nella frase di assegnazione v = e in F66 sono proibite le seguenti combinazioni

fra il tipo v ed il tipo di e:

v,k,v±k,s*v±k

Variabili dimensionate

Ricordiamo alcune caratteristiche delle variabili dimensionate in F66.

• Il massimo numero consentito di dimensioni è tre.

• Nel dichiaratore di variabile dimensionata è prevista, per ogni dimensione, la

dichiarazione della sola limitazione superiore, in quanto la limitazione inferiore è

uguale ad l.

• Non è previsto l'uso del dimensionamento indefinito.

• L'unica forma consentita di un dichiarato re di dimensione variabile è il nome

di una variabile intera, che deve far parte degli argomenti muti o di un blocco

COMMON nella stessa unità di programma.

• Ciascuna espressione indice nel nome di un elemento di variabile dimensionata

deve avere una delle forme seguenti:

Linee di commento

• In F66 una linea di commento è caratterizzata dalla presenza del carattere

C in colonna l. In F77 è possibile usare il carattere * e il carattere C.

Linee di continuazione

• In F66 sono consentite linee di continuazione che contengono qualsiasi carat­

tere nelle colonne dalla prima alla quinta, eccettuato il carattere C sulla prima

colonna. In F77 le colonne dalla prima alla quinta di una linea di continuazione

devono contenere dei caratteri blank.

Nome del programma principale

• In F66 non è prevista la possibilità di dare un nome al programma principale;non esiste infatti l'istruzione PROGRAM.

Dati di tipo carattere

• In F66 non esiste il tipo carattere ma esistono le costanti di tipo Hollerith

ovvero costanti del tipo nH Cl c2 ... cn dove ogni Ci rappresenta un carattere.

Dichiarazione implicita di tipo

• In F66 non esiste l'istruzione IMPLICIT.

tipo di v

complesso

complesso

complesso

intero

reale

doppia precisione

tipo di e

intera (consentita in F77)

reale (consentita in F77)

doppia precisione (proibita anche in F77)

complessa (consentita in F77)

complessa (consentita in F77)

complessa (proibita anche in F77)

~ ~!

l''Il\

Nome simbolico di costante

• In F66 non esiste l'istruzione PARAMETER e quindi non esiste la possibilitàdi dare nomi simbolici alle costanti.

dove v è una variabile intera e k ed s sono costanti intere.

• Il valore di un indice nel nome di un elemento di variabile dimensionata puòsuperare la corrispondente limitazione superiore, purché la posizione di quel­

l'elemento in memoria non superi l'ampiezza totale della variabile dimensionata

stessa.

Page 197: Fortran

386

• E' consentito usare in una frase EQUIVALENCE il nome di una variabile di­

mensionata seguito da un solo indice, anche se le sue dimensioni sono più di una.

Istruzioni di controllo

• In F66 non esiste il costrutto IF-THEN-ELSE.

• La sola forma consentita per l'istruzione GOTO-calcolato è la seguente

GOTO (e l , ..., et), v

dove ciascuna ei è un'etichetta e v una variabile di tipo intero. Inoltre, a diffe­

renza di quanto è previsto in F77, se il valore di v non è compreso fra l e k non

è stabilito quale istruzione debba essere eseguita dopo l'istruzione GOTO-cal­colato.

• L'istruzione DO in F66 ha la forma seguente:

DO n v = mI' m2, m3

dove: n è l'etichetta del1a frase terminale; v, la variabile del DO, è di tipo

intero; mI' m2 e m3 sono il parametro iniziale, finale e d'incremento e possono

essere nella forma di costante o variabile di tipo intero. Il parametro m3, come

in F77, può essere omesso ed il suo valore in questo caso è assunto essere 1.

Devono inoltre valere le seguenti condizioni: mi' m2

, m3

> O e mi ~ m2. Al

termine de11'esecuzione del ciclo-DO la variabile di controllò è indefinita. Si os­

servi che in F66 è permesso l'uso del rango esteso, proibito invece in F77.

Istruzioni di l/O

• In F66 non esistono le seguenti possibilità ed istruzioni:- Le istruzioni guidate dal1a lista;

- Il controllo del1e condizioni di errore e fine file;

- Le istruzioni OPEN, CLOSE e INQUIRE;

- I descrittori Iw.m, Ew.dEc, Gw.dEc, BN, BZ, S, SP, SS, :, Tn, TLn, TRn,'hl' .. hn ' ;

- Le operazioni di l/O ad accesso diretto.

• L'unica forma consentita in F66 per le frasi di l/O con formato è la seguente:

READ (u, f) lista

WRITE (u, f) lista

dove: u è una costante o variabile di tipo intero che identifica l'unità di l/O (solo

come file esterno); f ~ l'etichetta di una frase FORMAT o il nome di una variabile

dimensionata definita in modo tale da contenere dei caratteri costituenti una spe­

cificazione di formato; la lista è costituita da eventuali liste con DO-implicito e

nomi di variabile, nomi di elementi di variabile dimensionata e nomi di variabile

dimensionata. In ogni caso la lista non deve contenere espressioni. Nel1e liste con

387

DO-implicito la specificazione v = mI' m2, m3 prevede che: v sia una variabile

di tipo intero; mI' m2, m3 siano variabili o costanti di tipo intero con le limita­zioni già viste per l'istruzione DO.

• In una operazione di ingresso la definizione degli elementi della lista avviene

solo al completamento dell'esecuzione dell'intera operazione di lettura.

• Nelle operazioni di l/O con formato è possibile trasmettere sequenze di carat­teri tramite il descrittore Aw. Tali sequenze possono essere associate ad elementi

della lista di l/O di tipo qualsiasi; la lunghezza massima di ogni sequenza è legata

al tipo dell'elemento ad essa associato nella lista di l/O.

• In F66 è possibile usare il descrittore n HCI ... cn in specificazioni di formato

associate ad istruzioni di ingresso.

• In F66 il descrittore Dw.d deve essere associato a dati di tipo doppia precisione

ed i descrittori Fw.d, Ew.d, GW.d a dati di tipo reale.

Sottoprogrammi

• In F66 non sono previsti ritorni alternativi dai sottoprogrammi.

• In F66 non sono previsti nomi generici, ma solo specifici, per le funzioni in­

trinseche. Le seguenti funzioni intrinseche non esistono in F66: tutte le funzioni

che trattano dati di tipo carattere e DINT, ANINT, DNINT, NINT, IDNINT,

DDIM, DPROD, TAN, DTAN, ASIN, DASIN, ACOS, DACOS, SINH, DSINH,

COSH, DCOSH e DTANH. Non esiste, in F66, l'equivalente della funzione INT

applicata ad un argomento di tipo intero o complesso; analogamente non esiste

l'equivalente della REAL applicata ad un argomento di tipo reale; la funzione

CMPLX si applica solo ad una coppia di argomenti reali e la funzione DBLE si ap­

plica solo ad un argomento reale. In F66 le funzioni AMOD, MOD, SIGN, ISIGN

e DSIGN non sono definite quando il valore del secondo argomento è zero.

• Le seguenti funzioni intrinseche in F66 non possono essere argomento attuale

corrispondente ad un argomento muto di tipo sottoprogramma: ABS, IABS,

DABS, AINT, INT, IDINT, AMOD, MOD, AMAXO, AMAXl, MAXO, MAXl,

DMAXl, AMINO, AMINl, MINO, MINI, DMINl, FLOAT, IFIX, SIGN, ISIGN,

DSIGN, DIM, 101M, SNGL, REAL, AIMAG. DBLE, CMPLX e CONJG.

• Le funzioni intrinseche usate come argomento attuale in corrispondenzaad un argomento muto di tipo sottoprogramma devono figurare in una frase

EXTERNAL; la frase INTRINSIC infatti, non esiste in F66. La frase EXTERNAL,

in F66, ha il solo scopo di dichiarare i nomi dei sottoprogrammi che figurano co­

me argomenti attuali corrispondenti ad argomenti muti di tipo sottoprogramma.

• In F66 non esistono le istruzioni SAVE ed ENTRY.

Istruzione DATA

• In F66, nel1a forma nlista/vlista/ che figura in una frase DATA, nlista può

Page 198: Fortran

388

essere costituita solo da nomi di variabile e nomi di elementi di variabile dimensio­

nata con indici nella forma di costanti intere.

Sottoprogrammi BLOCK DATA

• L'unica forma consentita, in F66, della prima istruzione di un sottoprogramma

BLOCK DATA è quella senza nome.

A3. Ordinamento delle istruzioni F77

Le istruzioni F77 possono essere raggruppate in:

l. Istruzioni iniziali: PROGRAMFUNcnONSUBROUTINEBLOCK DATA

2. Istruzioni di specificazione: IMPUCITPARAMETERINTEGERREALOOUBLEPRECISIONCOMPLEXLOGICALCHARACTERDIMENSIONEQUIVALENCECOMMONEXTERNALINTRINSICSAVE

3. Istruzione DATA

4. Funzioni definite da una frase

5. Istruzioni eseguibili: Assegnazione aritmetica, logica, carattere

Controllo: IF(c) THENELSE IFELSEENDIFIF-logicoIf'-aritmeticoGOTO - incondizionatoGOTO· calcolatoGOTO - assegnato (*)DOCONTINUESTOPPAUSE(*)END

Istruzione: CALL

Istruzione: ASSIGN (*)

(*) Questa istruzione non è stata trattata nel testo in quanto di scarsa utilità.

Page 199: Fortran

390 391

Ingresso/uscita: READ

WRITEPRINTOPENCLOSEINQUIREBACKSPACEENDFILEREWIND

6. Istruzione ENTRY

7. Istruzione FORMAT

8. Linee di commento

• La prima frase di ogni unità di programma deve essere una istruzione iniziale.L'istruzione PROGRAM può essere soltanto la frase iniziale del programma prin­cipale.

• L'ultima frase di ogni unità di programma deve essere un'istruzione END.

In un programma principale o in un sottoprogramma di tipo FUNCfION oSUBROUTINE le istruzioni devono rispettare iI seguente ordinamento:

• Tutte le istruzioni di specificazione devono precedere tutte le frasi DATA, lefunzioni definite da una frase e le istruzioni eseguibili;

• tutte le funzioni definite da una frase devono precedere tutte le istruzioni ese­guibili;

• le frasi DATA possono comparire in qualsiasi punto dopo le istruzioni di spe­cificazione;

• le istruzioni ENTRY possono comparire in qualsiasi punto che non sia dentroal rango di un DO o tra un'istruzione IF(c) THEN e la corrispondente istruzioneEND IF;

• le istruzioni FORMAT e le linee di commento possono comparire in qualsiasipunto.

Per le frasi di specificazione è inoltre fissato il seguente ordinamento:

• le istruzioni IMPLICIT devono precedere tutte le altre istruzioni di specifica­zione;

• ogni istruzione di specificazione che indica il tipo di un nome simbolico di co­stante deve precedere la frase PARAMETER che definisce quel particolare nomesimbolico di costante;

• la frase PARAMETER deve precedere tutte le altre istruzioni che contengonoi nomi simbolici di costanti da essa definiti.

Queste regole sono riassunte nella figura seguente nella quale le linee orizzontali

dividono gruppi di istruzioni che non possono essere mescolate mentre quelle

verticali delimitano istruzioni che possono essere presenti contemporaneamentein qualsiasi ordine.

Istruzione iniziale: PROGRAM, FUNCTION, SUBROUTINE,BLOCK DATA

Istruzioni IMPLICITIstruzioni

PARAMETERIstruzioni Altre istruzioni di specificazione

Linee di FORMATcommento ed

Istruzioni Funzioni definite da una fraseENTRY

DATAIstruzioni eseguibili

Istruzione END

Ordinamento delle istruzioni F77 in una unità di programma.

Page 200: Fortran

393

A4. La codifica dei caratteri64 blank 123 rI' 161 214 o6~74 124 @ 162 • 215 p

in ASCII e in EBCDIC75 . 125 163 t 216 Q

76 126 - 164 u 217 R77 ( 127 ..

165 21HZ4y

78 + 128 166 w 22579 I 129 • 167 )( 226 S80 & 130 b 168 v 227 T

81-89 131 c 169 z 228 U

90 ! 132 d 170-191 229 V91 I 133 e 192 230 W92 * 134 f 193 A 231 X93 135 g 194 B 232 y

94 136 h 195 C 233 Z

Codice ASCII 95 137 1 196 O 231r-Z3996 - 13&-144 197 E 240 O

Il codice ASCII definisce 128 caratteri utilizzando per ciascuno 7 bits. I carat- 97 I 145 j 198 F 241 1

teri riproducibili in stampa sono i seguenti: 9&-106 146 k 199 G 242 2107 , 147 l 200 H 243 3108 l 148 Il 201 I 244 "109 149 n 202-208 245 5

32 blank 56 8 80 P 104 h 110 150 209 J 246 6> o 247 7

33 ! 57 9 81 Q 105 111 ? 151 p 210 K 248 834 .. 58 82 R 106 j 112-120 152 211 L 249 9q35 " 59 83 S 107 k 121 153 r 212 ..36 S 60 < 84 T 108 l 122 154--160 213 N

37 X 61 . 85 U 109 Il

38 & 62 > 86 V 110 n

Il39 63 ? 87 W 111 o Nelle tabelle riportate i numeri decimali che accompagnano ciascun carattere40 64 @ 88 X 112 p sono i corrispondenti numeri d'ordine.41 65 A 89 y 113 q42 * 66 B 90 Z 114 r43 + 67 C 91 [ 115 s44 , 68 D 92 \ 116 t45 - 69 E 93 J 117 u46 70 F 94 118 v47 I 71 G 95 119 w48 O 72 H 96 120 x49 1 73 I 97 a 121 y50 2 74 J 98 b 122 z51 3 75 K 99 c 123 {52 4 76 L 100 d 124 I53 5 77 .. 101 e 125 l54 6 78 N 102 f 12655 7 79 O 103 9

Codice EBCOIC

Il codice EBCOIC utilizza 8 bits per la codifica di ciascun carattere; esso com­prende tutti i caratteri del codice ASCII ordinati però in modo diverso.

Page 201: Fortran

Bibliografia

(1] DAHL O.J., HOARE C.A.R., DIJKSTRA E.W. (1972): Structured Programming, AcademicPress, New York.

[2] CHURCH A. (l956):Introduetion to mathematicallogic I, Princeton UnivoPresso

[3] ANDRONICO A. ed altri (1973): Scienza degli elaboratori, Zanichelli, Bologna.

[4] WINSTON D., HORN B.K.P. (198 I): L/SP, Addison Wesley.

[5] NAUR P. (1963): Revised report on the Algorithmic LanguageAIgol60, Comm. ACM voI.6, n. 1.

[6] LECARME O., NEBUT J.L. (1985): Pascal - Guida per programmatori, McGraw-Hill.

(7] Mc CARTHY J. (1963): A basis for a mathematical theory of computation, Proc. IFIPCongress 1962, North-Holland Pub. Co., Amsterdam.

[8] HERMES H. (1955): Entscheidungsprobleme in Mathematik und Logik, Ausarbeitungeiner Vorlesung, Aschendorft, Mtinster i.w.

[9] FONTANELLA F., PASQUALI A. (1979): Calcolo numerico. Metodi ed algoritmi, PitagoraEd., Bologna.

(10] FORSYTHE G.E., MALCOLM M.A., MOLER C.B. (1977): Computer methods for Mathe­matical Computations, Prentice-Hall, Englewood Cliffs.

[II] FORSYTHE G.E., MOLER C.B. (1967): Computer Solution of Linear Algebraic Systems,Prentìce-Hall, Englewood Cliffs.

(12] ANSI X3.9·1978 - American National Standards Inst. NewYork.

[13] ANSI X3.9-1966 - American National Standards Inst. New York.

[14] GoLUB G.H., VAN LoAN C.F. (1983): Matrix computations, John Hopkins Univo Presso

[15] MEYER B., BAUDOIN C. (1978): Méthodes de programmation, Eyrolles.

Page 202: Fortran

Indice analitico

I numeri in neretto si riferiscono alle Appendici.

A, 195, 204,209ACCESS =. 360, 362, 369, 371Accesso, vedi: fileAccumulatore, 23Albero delle chiamate, 240,347Alfabeto, 48, 185Algoritmo, 3, 239, 245, 252Allungamento, 181, 185

vedi: blocco COMMONAmpiezza

argomento, 279, 288campo, 194,204dimensione, 153, 288variabile dimensionata, 153, 160

.AND.,78Annidamento

ciclo-DO, 145DO-implicito, 221struttura decisionale, 105

Apice, 48, 92, 174, 196, 205, 2I7, 384Apostrofo, 174Argomento, 73,187,189,312

vedi: ampiezza, lista, lunghezza, ordineasterisco, 245, 298attu~e,243,249,256,260,275, 288,293,298,307,333,336,340carattere, 289costante, 276di ingresso, 243, 250di uscita, 243, 250, 276espressione, 74, 276muto, 243,245, 249, 253, 256, 259, 275, 288,307,316,322, 331,341,384funzione intrinseca, 298, 387sottoprogramma, 245, 249, 253, 256, 292,387variabile, 245, 249, 253, 256variabile dimensionata, 245, 249, 253, 256, 277

Aritmeticavedi: assegnazione, espressione

if'l-I

; I

Page 203: Fortran

398

finita, 41intera, 68, 138, 268reale, 68, 138

Arrotondamento, 39, 201, 263, 265vedi: esempi

ASCII, 173,185,268,392Assegnazione, 3, 83, 90,157,180,184,260,291,323,372

aritmetica, 83, 322, 385, 389carattere, 180,204,322,389logica, 83, 86, 389mista, 85simbolo, IO, 83

Assemblatore, 26ASSIGN,389Associazione, 243, 250, 260,276,292,307,31 IAsterisco, 48,50,61,197,205,228,382

vedi: DATA, dimensionamento indefinito, identificatore di formato, lunghezza indefinita,PRINT*, READ*, ritorno alternativo

Attivazioneciclo-DO, 128, 140sottoprograrnma, 241, 249, 257, 275, 289, 307, 336, 339, 347

Aw, 195,203.209,387

BACKSPACE, 355,366, 390Base di numerazione, 33, 37Bit, 22, 173Blank,48, 174, 18~ 376,384

vedi: A, Aw, BLANK =, BN, BZ, Gw.d, nX, READ *,spaziatura, TnBLANK = ,360, 363, 372Blocco COMMON, 280, 288, 307,309,312,319,341,381,384

vedi: COMMON, lunghezzaallungamento, 319etichettato, 307, 310, 322, 325, 347indefinito, 347nome,307,310,348,381non etichettato, 308, 311, 322, 347

Blocco ELSE, 103,116Blocco THEN, 103BLOCK DATA, 243, 293, 322, 325, 381,387,389BN, 196,231,363,386Byte, 22, 35, 354BZ,196,231,363,386

CALL, 249, 335, 389Campo, 194,209,228,233,358,363

vedi: ampiezzaCarattere

vedi: A, Aw, argomento, assegnazione, CHARACTER, costante, espressione, funzione

399

esterna, ingresso/uscita, lunghezza, ordine, unità di memoria, variabilecodificabile, 173, 185, 189, 392iniziale e finale. vedi: esempispeciale, 48tipo, 173,308,337,382,384

Caratteristica, 37, 40,201,228Caricamento. 24Cella. vedi: locazioneCHAR, 189,268,382CHARACTER, 57, 174,253,337,389Chiamata, 240, 275

ricorsiva, 14,277Ciclo, 125

vedi: annidamento, DO, UNTIL, WHILEfinito, 127, 131iterativo, 12, 128, 131, vedi: esempi

CLOSE,364,38],386,390Codice operativo, 23Colonna, 50, 384Commento, 50,38],384,390COMMON 307, 316, 319, 325, 332,382,389Compilatore, 26, 57,153,162,277,312Compilazione, 26, 244, 275, 321,325Complemento a due, 36Complesso

vedi: assegnazione mista, COMPLEX, costante, descrittore, espressione mista, ingresso/uscita,operazione

COMPLEX, 57, 253,38],389Concatenazione, I Il,179,208,291,382Conne~ione, 10,359,361,364,373Contatore

vedi: DO, ripetizioneContinuazione, 5 I , 38] , 384CONTINUE, 119, 129,136,146,389Controllo

vedi: istruzione, lista, spaziatura, trasferimento del controllo, unitàConversione, 33, 37, 71, 75, 197,317, 322,358

vedi: funzione intrinsecaCorpo

vedi: ciclo iteratìvo, sottoprogrammaCoUank,4~53.90,96,276,321,323,382

vedi: argomento, dimensionamento, espressione, PARAMETERcarattere, 56,92, 174, 205, 216, 289, 382complessa, 55, 202doppia precisione, 55, 199intera, 53, 153,156,174,198,230,233logica, 56nome, 54,96, 153, 174, 176, 258,321,384,390reale, 54, 199

Page 204: Fortran

400

D,55,201DATA, 321, 323, 325,381,387,389'DELETE', 365Descrittore non ripetibile, 195,202,210,215,218,231,382

di tabulazione, 230Descrittore ripetibile, 195,209,212,228,233,358,382

carattere, vedi: A, Awcomplesso, 202intero, vedi: Iw, IW.mlogico, vedi: Lwreale, 199,202,209,228, vedi: Dw.d, Ew.d, Ew.dEc, Fw.d, Gw.d, GW.dEc

Diagnostico, 26, 28Diagramma, 9, 12Dichiarativa

vedi: istruzioneDichiaratore

dimensione, 153, 160, 280, 288, 381dimensione indefinita, 288dimensione variabile, 280, 288, 385variabile dimensionata, 153, 160, 308, 332, 385

DlMENSION, 155,389Dimensionamento

costante, 153, 308indefinito, 288, 385variabile, 280, 285, 288, 313,332

Dimensione, 156, 167,278vedi: ampiezza, dichiaratore

'maser', 362, 368, 373DlRECT =, 372D~c~ 22,351,360,368dnr, 195, vedi: descrittore non ripetibileDO, 128, 132, 141,333,381,386,389

vedi: annidamento, DO-implicitociclo, 133, 138, 145contatore, 127, 133, 135, 220frase terminale, 132, 136,145,147,333parametro, 133,381,382rango, 133, 135, 137, 141, 145,220,390variabile, 133, 136, 143,145,381

DO-implicito, 219, 321, 323, 381,382,386Dollaro, 48Doppia precisione

vedi: assegnazione mista, costante, descrittore ripetibile, DOUBLE PRECISI0N, espressionemista, ingresso/uscita, precisione

DOS, 31, 369DOUBLE PRECISION, 57, 253,381,389dr, 195, vedi: descrittore ripetibileDue punti, 48, 231, 381, 384, 386

vedi: dichiaratore di variabile dimensionata, sottostringaDw.d, 195, 199,201,209,233,382,386

E,54, 201,228EBCOIC, 173,392Elemento di variabile dimensionata, 151,160,178,279,289,355,375,385

nome, 156,277,292,316,321,357,364posizione, 160

Elevamento a potenza, 67ELSE, 102, 105, 112, 114, 136, 142,389

vedi: blocco ELSEELSEIF,112,114,136,141,389END,93,136,206,244,321,325,389ENDFILE, 354, 390END IF, 102, 105, 112, 114, 136, 142,333,389,390END =,355,357,386ENTRY, 331, 336, 338,341,381,387,390.EQ., 76,185Equazione di 2° grado, vedi: esempiEQUIVALENCE, 316, 325, 374,382,386,389.EQV., 78, 381,384Errore

arrotondamento, 40, 169,248assoluto, 40condizione di, vedi: ERR =programmazione, 28,58, 131, 275relativo, 40

ERR =, 354, 357, 360, 363,365,372,374,382,386Esecuzione, 83, 101,208,210,212,223,245,257,260,275,298,307,331,339

vedi: programmaEsempi

arrotondamento, 377carattere iniziale e finale, 289ciclo itera tivo, 12, 129equazione di 2° grado, 107,247,252fattoriale, 17,254,257massimo e minimo, 4,7,15,116,119,246,252,281media aritmetica, 125, 136, 142,145,168,239norma,282,295,338,340ordinamento, 110,115,166,313polinorrUo, 163,334,336precisione di macchina, 255prodotto, 6,15,138prodotto scalare, 167, 169radice quadrata, 129, 131, 144,246,251simulazione della ricorsività, 344somma, 6, 14, 16,23,25,137,278

Esponente, 54,67,92,199,233Espressione, 61,83,91, 157,259,276,382,386

aritmetica, 61, 76,83,120,133,153,385carattere, 179, 184, 189,205,207,289,360costante, 79,96, 174, 258, 316,321,324, 363, 365,385di sottostringa, 179, 321

401

Page 205: Fortran

402

indice, 156,160,321, 381, 384intera, 223, 280, 298, 354, 356, 359, 362,369logica, 77, 103, 112, 116,385mista, 70,384relazionale, 76, 185valutazione, 62, 69, 74, 76, 78

Etichett~25,49, 51,101,103, 120, 13~ 205, 299,307,358,364Ew.d, 195, 199,201,209,233,387Ew.dEc, 195, 209, 228, 233,386EXIST =, 372EXTERNAL, 292, 333, 387,389

Fattore di scala, vedi: sPFattoriale, vedi: esempiFile, 222, 351, 359

accesso diretto, 352, 362, 367, 371, 373, 382,386con formato, 362connesso, 359, 364; 372esterno, 222, 352, 356, 358, 371, 381, 382fine, vedi: ENDFILE, END =, recordinterno, 352, 356, 358, 375, 381nome, 360, 372preconnesso, 359, 364senza formato, 362sconnesso, 364sequenziale, 222,351,356,362,365,373stato del, 361

FILE =, 360,371,374Floating point, 37, 70, 264f1(x), 39Floppy disk, 22, 368Flusso, 3,101,242

diagramma di, 12FMT =, 355, 356, 382FORM =, 360, 362,371FORMAT, 205, 382, 386, 390Formato, 92

vedi: file, identificatore di formato, record, specifìcatore, specificazionedella linea, 50

'FORMATTED', 362, 373FORMATTED =, 372Frase, vedi: istruzioneFull language, 47,381FUNCTION, 243, 253, 293, 337,339,389Funzione definita da una frase, 259, 389, 390Funzione esterna, 252, 340

vedi: FUNCTION, lunghezzacarattere, 258, 382nome, 253,256,338

prima istruzione, vedi: FUNCTIONriferimento, 256tipo, 253, 256, 337valore, 252, 337

Funzione intrinseca, 71, 261, 293,382vedi: argomentoconver~one, 262, 298manipolazione dei caratteri, 187,267,298,387matematiche, 265altre, 268nome, 262,265,298,382

Funzione ricorsiva, 14,344Fw.d, 199,200,209, 233,387

.GE., 76, 185GOTO-assegnato, 136,389GOTO-calcolato, 120, 381, 386, 389GOTO-incondizionato, 101, 121, 129, 136,389.GT., 76,185Gw.d, 195,209,229,382,387Gw.dEc, vedi: GW.d

H, vedi: n H h I ... hnHardware, 21Hollerith, 384'hl' .. hn ' , vedi: n H hl ... hn

ICHAR, 189,268Identificatore di formato, 205, 217, 223, 356,381IF-aritmetico, 121, 136, 389IF-Iogico, 117, 119, 129,389IF-THEN-ELSE, 102, 119, 136,140,333,386,389,390IMPLICIT, 58, 177,254,325,384,389,390Incremento, 134Indentation, 107INDEX, 188, 268, 382Indice, 152, 156, 160, 165, 286, 316, 384

vedi: espressioneIndirizzo, 23,275, 278, 289, 292,307

assoluto, 28relativo, 26

Inf j : sUPi, 153Ingresso/uscita

vedi: istruzione, lista, operazione, simbolo, unitàdati carattere, 183, 203, 209dati complessi, 202dati interi, 198, 209

403

Page 206: Fortran

404

dati logici, 230dati reali e doppia precisione, 199,202,209,386guidata dalla lista, 90, 183, 193, 202, 204, 224, 381,386variabile dimensionata, 164, 167

INQUlRE, 371,374,381,386,390INTEGER, 57, 253,389Intero

vedi: aritmetica, costante, espressione, ingresso/uscita, INTEGER, Iw, lw.m, rappresentazioneInterpretatore, 18, 29INTRINSIC, 298, 387, 38910STAT =, 354,357,360,363,372,374Istruzione, 3, 23,48,51

vedi: ordineassegnazione, 3, 291, 323controllo, 386, 389dichiarativa, 49,57,244,277,280,321,389,390dichiarativa di tipo, 154, 174,253,325,337dipendente, 116eseguibile, 49, 389,390finale, vedi: istruzione terminaleingresso/uscita, 89,193,205,222,351,355,381,386,389iniziale, 103, 105, 141,242,389,390posizionamento, 366ritorno, 242specificazione, vedi: istruzione dichiarativaterminale, 103, 105, 112, vedi: DO

lw, 195,198,209lw.m, 195,209,228,382,386

'KEEP', 365

.LE., 76,185LEN, 190,268, 382LGE, 187,268,298LGT, 187,268,298Linea, 50,90,92

vedi: commento, continuazioneLinguaggio, 21, 23, 25, 31Linker, 28, 222, 312, 359Lista

vedi: DO-implicitoargomenti, 250, 256, 275, 280, 288, 292, 298, 312,322, 331controllo, 355, 358, 369ingresso/uscita, 90, 157, 164, 183, 197,205,208,212,214,218,222,256,354,358,

371,382,386,387programma, 50

LLE, 187, 268, 298LLT, 187,268,298

s

405

Locazione, 22, 83,151,160,163,253,275,310,339LOGICAL, 57, 253,389Logico

vedi: costante, espressione, ingresso/uscita, LOGICAL, Lw, operatore.LT., 76, 185Lunghezza

vedi: specificatoreargomento, 289blocco COMMON, 309, 320complessiva, 292dato carattere, 173, 178, 268, 382funzione esterna, 258indefinita, 176,258,290,337record,21~353,362,369,371,373,376

sottostringa, 179Lw, 195,209,230

Mantissa, 37,40,201Massimo o minimo, 268, 298

vedi: esempiMatrice, 152, 154, 161,286Media aritmetica, vedi: esempiMemoria, 22,351,365,375Modulo oggetto, 28Monoprogrammazione, 31Multiprogrammazione,31

NAME =, 372NAMED =, 372Nastro, 22, 351, 360.NE., 76, 185.NEQV., 78, 381, 384NEXTREC =, 372, 374'NEW', 361nHh\ ... hn, 196,216,387Nido, 105'NO', 373Nome

vedi: costante, elemento di v. dimensionata, file, funzione esterna, funzione intrinseca,programma, punto di ingresso secondario, sottoprogramma, sottostringa, variabile,variabile dimensionata

generico, 262, 265, 298, 382,387locale, 244,310simbolico, 25,49,59,151, 174,239,245,253,259,298,307,323,325,331,341specifico, 262, 265, 298, 387

Norma, vedi: esempi.NOT.,78'NULL', 363,373

Page 207: Fortran

\ I

406

NUMBER =, 372nX, 196,215,230

'OlD: 361. 363OPEN,222,353,358,365,382,386,390OPENED =, 372.OR.,78Operatore

aritmetico, 61concatenazione, 179logico, 77priorità, 62, 71, 78relazione, 76, 185

Operazionel'cdi: ordinecomplessa, 70conversione, 71, 73elemen tare, 41ingresso/uscita, 89, 209,231,256,351,355,387primitiva, 3simbolo, 9

Ordinamento, vedi: esempiOrdine

argomenti, 250, 256, 336caratteri, 185istruzioni, 49, 383, 389, 391operazioni, 62, 64, 69

Overtlow, 35, 39, 54,68, 138. 254

P, vedi: sPPARAMETFR, 96,176,258,323,325,38],384,389,390Parametro. vedi: argomento. DOParentesi, 48. 64,73,78. 174, 195, 210,219,245,253,333,336,340,382Parola chiave, 49PAUSE,389Preconnessione, 359.364Polinomio, vedi: esempiPrecisione

di macchina, 40, 92, 130, 255doppia, 41, 169,200,202.264finita, 130semplice, 41,169,200.264

Predefinizione, 322PRINT,256,381,390PRINT r, 205, 223,382PRINT·,91.223,289Prodotto, 269, vedi: esempi

scalare, vedi: esempi

407

PROGRAM, 93, 384, 389, 390Programma, 21, 89, 239, 275, 307,311,325,359

vedi: lista, unitàesecuzione, 28, 241, 310, 323, 341, 347.363eseguibile, 28, 241nome,93,384 .oggetto, 26, 28princip~e,239, 241,307,347,384,390sorgente, 26

Punto di ingresso secondario, 331vedi: ENTRYnome, 332,336,339riferimento, 335, 340tipo, 337

Punto di riscansione, 210

Radice quadrata, vedi: esempiRango, vedi: DORappresentazione, 33

esterna, 197, 201, 203, 229, 232, 353finita, 39, 70interna, 197,200,202,262,352

READ, 355, 390READ f, 205, 223, 382READ (u, f), 222,386RE AD. , 90, 205, 223REAl, 57, 75, 253,389Reale

vedi: aritmetica, costante, descrittore ripetibile, espressione, ingresso/uscita, rappresentazioneREe =, 355, 359, 369RECl =,360,362,369,372Record, 194, 197,201,212,222,351,366

vedi: lunghezzacon formato, 352, 362, 371corrente, 209,212,214,218,230end fik.352,354,35~366

numero d'ordine, 369senza formato, 352,362,371, 373

RETURN, 136, 244, 298REWIND, 355, 365, 390Ricorsività, 14, vedi: esempiRipetizione, 125, 130, 133,220,324

contatore, 127. 134. 195simbolo, 9

Ritorno alternativo, 249, 298. 301, 382, 387

S, 196,232,382,386SAVE, 325,341,348,38],387,389

Page 208: Fortran

408

Sbarra, 48vedi: COMMON, concatenazione, descrittore non ripetibile, operatore, READ., SAVE

Scambio, 87di informazioni, 243,275,313,331,341

'SCRATCH', 361, 365'SEQUENTIAL', 362, 373SEQUENTIAL =, 372sf, 195, vedi: specificazione di formatoSimbolo, ':J

tavola, 26, 322Software, 21Somma, vedi: esempiSottoprogramma, 239, 275, 292, 307, 331, 387, 390

vedi: argomento, attivazione, BLOCK DATA, funzione esterna, funzione intrinseca, puntodi ingresso secondario, SUBROUTINE

chiamata, vedi: attivazionecorpo, 243, 253,280,288,325,331,333esterno, 292nome, 73, 243, 249, 253,256,292prima fase, 242, 332uscita, 241

Sottostringa, 178,180,182,207,289,355,375,382vedi,' espressione, lunghezzanome, 179,292,316,321

SP,196,232,382,386sP, 196,233Spaziatura

l'cdi: blankverticale, 214

Specificatoreformato, 356lunghezza, 174, 177lunghezza indefinita, 176, 258, 290, 337ritorno alternativo, 249, 299stato, vedi: 10STAT =, STATUS =tipo, vedi: CHARACTER, COMPLEX, DOUBLE PRECISION, INTEGER, LOGICAL,

REALunità, vedi: UNIT =

Specificazionevedi: istruzioneformato, 194,205,208,212,214,224,232,354,358,363,371,382formato variabile, 208, 226vuota, 214

SS,196,232,382,386Stampante, 92,214,351,360STATUS =, 360, 365

. STOP, 93,136,242,244,389Stringa, 173, 180,182,185,188,203,217,289

vedi: lunghezza dato carattereStruttura decisionale, 102, 105, 111, 114, 140

409

vedi: annidamento, IF-THEN-ELSEStruttura di ripetizione, 125

vedi: DOSUBROUTlNE, 243, 245, 292, 298, 334, 389

vedi: CALLSubset language, 47,381sup], 153,381,384Supervisore,31

Tavola dei simboli, 26,322Testina di lettura/scrittura, 352, 365, 368Time-sharing, 31Tipo implicito, 58, 177,254,384

vedi: IMPLICITTLn,196,230,382,386Tn,196,230,382,386Tolleranza, 77, 131Traduttore, 18, 25Traduzione, 28Trasferimento del controllo, 101,104,137,143,147,242,299,331TRn,196,230,382,386Troncamento,39, 181,263

Underf1ow, 39, 54'UNFORMA TTED', 362, 373UNFORMATTED =, 372UNIT =, 354,360,365, 371,382Unità

aritmetica, 22attivante, 241, 243, 250, 258, 275, 288, 292, 299, 307,331,333,341,347di controllo, 22di ingresso/uscita, 22, 89,210,212,222,351,354,359,364,371,375di memoria carattere, 173, 182,289, 292, 307,310di memoria numerica, 22, 307, 310di programma, 21, 239, 242, 260, 275,293,298,307,309,311,316,319,358,364,

383,390numero di, 222, 354, 373, 381

'UNKNOWN', 361, 373UNTlL,128

Variabile, 56vedi: DO, DO-implicitocarattere, 174,289,356,375interna, 341, 348nome di, 56,83,245, 249,253,256,275,280,308,316,321,342,357,364tipo, 56,275

Variabile dimensionata, 151, 153, 156

Page 209: Fortran

I:l

Ii

II

I I

410

vedi: ampiezza, argomento, dichiaratore, elementonome, 153, 155, 164, 178,205,208,245,249,253,256,298,308,316,321,342

Vettore, 152, 154, 160Video, 92, 351Virgola, 48, 73,90,120, 133,218,231,308,316,321,348,354

l'cdi: floating point

WHILE,128WRITE, 256,355,390WRITE (u, f), 222, 386

X, vedi: nX

'YES',373

'ZERO', 363. 373

Page 210: Fortran