ΚΕΝΤΡΟ ΠΛΗ.ΝΕ.Τ. Ν. ΦΛΩΡΙΝΑΣ

Η Γλώσσα Προγραμματισμού Fortran 90/95

Τι Είναι η Fortran

Η Fortran (FORmula TRANslation) είναι μια επιστημονική γλώσσα προγραμματισμού, όπως είναι οι Cobol, Algol, Ada, PL1, APL, Pascal κ.ά., η παλαιότερη απ’ όλες. Ένας πολύ μεγάλος όγκος από επιστημονικές εφαρμογές έχει αναπτυχθεί με τη γλώσσα αυτή και έτσι είναι αναγκαία και χρήσιμη η εκμάθηση και η υποστήριξή της. Η Fortran είναι εξαιρετικά κατάλληλη για πολύπλοκες αριθμητικές εργασίες.

Δημιουργήθηκε το 1955 στα εργαστήρια της ΙΒΜ από μια ομάδα επιστημόνων με επικεφαλής τον John Backus. Μέχρι σήμερα έχουν εμφανισθεί διάφορες παραλλαγές και βελτιώσεις της, όπως οι Fortran ΙΙ, Fortran IV, Fortran V, Fortran 66 και Fortran 77.

Η Fortran 90 είναι η πιο τελευταία έκδοση της γλώσσας και με την επερχόμενη Fortran 95 τοποθετείται πλέον στον όμιλο των μοντέρνων γλωσσών προγραμματισμού. Υπάρχει και η έκδοση Visual Fortran, η οποία βασίζεται στην Fortran 90 με στοιχεία της Fortran 95 και χρησιμοποιεί ένα γραφικό, παραθυρικό περιβάλλον.

 

Το Πρώτο Πρόγραμμα σε Fortran

Για μια πρώτη γνωριμία με την Fortran, θα δούμε ένα απλό πρόγραμμα που υπολογίζει και εκτυπώνει την τρίτη δύναμη των ακεραίων από το 2 έως και το 100.

PROGRAM FIRST

! ΤΟ ΠΡΩΤΟ ΜΑΣ ΠΡΟΓΡΑΜΜΑ ΣΕ FORTRAN

! ΥΠΟΛΟΓΙΖΕΙ ΤΗΝ ΤΡΙΤΗ ΔΥΝΑΜΗ ΤΩΝ ΑΚΕΡΑΙΩΝ &

&! ΑΡΙΘΜΩΝ ΑΠΟ ΤΟ 2 ΕΩΣ ΚΑΙ ΤΟ 100

X=2    ! ΑΡΧΙΚΗ ΤΙΜΗ

100 Y=X**3

PRINT *, X, Y

X=X+1

IF(X<=100) GO TO 100

STOP

END PROGRAM FIRST

            Μερικές πρώτες παρατηρήσεις που μπορούμε να κάνουμε είναι οι εξής :

 

Γνωριμία με το Περιβάλλον της Visual Fortran

Το περιβάλλον της Visual Fortran είναι οργανωμένο σε projects και η ανάπτυξη των προγραμμάτων γίνεται δια μέσου των projects. Μέσα σε κάθε project δημιουργούνται τα αρχεία με τα πηγαία προγράμματα (source programs).

Τα projects είναι διαφόρων τύπων και περιέχονται μέσα σε workspaces, όπου ένα workspace μπορεί να περιέχει περισσότερα από ένα projects. Η Visual Fortran έχει ενσωματωμένο έναν δικό της text editor για να μπορούμε να γράφουμε τα προγράμματά μας και χρησιμοποιεί βιβλιοθήκες, που είναι πολύ χρήσιμες στους προγραμματιστές.

Για να ξεκινήσουμε την Visual Fortran, επιλέγουμε Developer Studio από το υπομενού Visual Fortran του αρχικού μενού Έναρξη. Για να δημιουργήσουμε ένα καινούργιο πρόγραμμα, επιλέγουμε New… από το μενού File ή πατάμε τα πλήκτρα Control+N.

Στο πλαίσιο διαλόγου New και στην καρτέλα Projects επιλέγουμε Fortran Console Application. Στο πλαίσιο κειμένου Project name γράφουμε το όνομα του project, π.χ. Project1. Στη θέση Location μπορούμε να αφήσουμε την προεπιλεγμένη θέση της Visual Fortran για τη δημιουργία του project, δηλ. την C:\Program Files\Microsoft Visual Studio\MyProjects\Project1, ή να κάνουμε κλικ στο διπλανό πλήκτρο με τις τρεις τελείες (…) και να επιλέξουμε μια άλλη δική μας θέση. Η Visual Fortran θα δημιουργήσει έναν φάκελο (directory) με το όνομα του καινούργιου project και στη θέση που επιλέξαμε.

Κάνουμε κλικ στο ΟΚ και στο επόμενο πλαίσιο διαλόγου επιλέγουμε το πλήκτρο επιλογής An empty project και κάνουμε κλικ στο πλήκτρο Finish. Στο νέο περιβάλλον που θα εμφανισθεί επιλέγουμε New… από το μενού File ή πατάμε τα πλήκτρα Control+N. Στο πλαίσιο διαλόγου New και στην καρτέλα Files επιλέγουμε Fortran Free Format Source File και στο πλαίσιο κειμένου File name γράφουμε το όνομα του προγράμματος, π.χ. Program1.

Στη θέση Location μπορούμε να επιλέξουμε τον φάκελο όπου θα δημιουργηθεί το πρόγραμμα ή αφήνουμε τον φάκελο που προτείνει η Visual Fortran. Κάνουμε κλικ στο ΟΚ και είμαστε έτοιμοι να ξεκινήσουμε να γράφουμε το πρόγραμμά μας.

Παρατηρούμε ότι καθώς πληκτρολογούμε τις εντολές του προγράμματος, αυτόματα η Visual Fortran χρωματίζει με πράσινο χρώμα τα σχόλια, με μπλε χρώμα τις εντολές της γλώσσας (δεσμευμένες λέξεις) και αφήνει όλα τα άλλα με το κανονικό μαύρο χρώμα. Αποθηκεύουμε το πρόγραμμά μας και βλέπουμε ότι προστίθεται αυτόματα η επέκταση .f90.

Για παράδειγμα, έστω ότι δημιουργούμε ένα πολύ απλό πρόγραμμα που θα προσθέτει δύο αριθμούς και θα εμφανίζει το άθροισμά τους :

! Πρόσθεση δύο αριθμών

program program1

    real::a, b, c

    read *, a, b

    c =a + b

    print *, a, b, c

    stop

end program program1

Για να εκτελέσουμε το παραπάνω πρόγραμμα, θα πρέπει να πάμε με τη σειρά στις εξής επιλογές του μενού Build :

Για να ανοίξουμε τώρα ένα υπάρχον πρόγραμμα και να το επεξεργαστούμε, επιλέγουμε Open Workspace… από το μενού File και αναζητούμε το αρχείο με όνομα Program1 αλλά με επέκταση .dsw.

 

Οι Σταθερές στη Fortran

            Οι σταθερές (constants) στη Fortran είναι έξι ειδών και είναι οι εξής :

 

Οι Μεταβλητές στη Fortran

            Οι μεταβλητές (variables) στη Fortran είναι κι αυτές έξι ειδών και είναι οι εξής :

INTEGER::A, FLORINA

REAL::K1, M5

DOUBLE PRECISION::MEAN, A ή REAL(8)::K1, M5

COMPLEX::A20, C

LOGICAL::RESULT, PASS

CHARACTER(LEN=μήκος)::A1, A2, A3, …

ή

CHARACTER(μήκος)::A1, A2, A3, …

ή

CHARACTER*μήκος::A1, A2, A3, …

Όλες οι παραπάνω εντολές ορίζουν ότι οι μεταβλητές Α1, Α2 και Α3 είναι αλφαριθμητικές και παίρνουν τιμές έως και μήκος όση είναι η τιμή του προσδιοριστικού μήκος. Αν παραλείψουμε την τιμή για το προσδιοριστικό, τότε οι μεταβλητές θα μπορούν να πάρουν τιμή ενός μόνο χαρακτήρα.

           

CHARACTER(LEN=8)::A1, A2*3, A3, Α4*5

που ορίζει ότι οι μεταβλητές Α1 και Α3 θα έχουν μήκος 8 χαρακτήρων, αλλά η μεταβλητή Α2 θα έχει μήκος 3 χαρακτήρων και η μεταβλητή Α4 θα έχει μήκος 5 χαρακτήρων.

Προσέξτε και τα εξής :

            CHARACTER A1(10)

CHARACTER *(*)B

CHARACTER(LEN=*)NAME

PARAMETER (NAME=’ΦΛΩΡΙΝΑ’)

Η μεταβλητή Α1 είναι ένας αλφαριθμητικός πίνακας μίας διάστασης που περιέχει 10 στοιχεία μήκους ενός χαρακτήρα το καθένα, το μήκος της μεταβλητής Β δεν προσδιορίζεται ενώ το μήκος της μεταβλητής NAME καθορίζεται στην επόμενη εντολή PARAMETER από την τιμή που της δίνουμε (μήκος = 7).

Το όνομα μιας μεταβλητής στη Fortran μπορεί να περιέχει γράμματα, ψηφία και τον χαρακτήρα υπογράμμισης _. Μπορεί να έχει έως και 31 χαρακτήρες αλλά ο πρώτος χαρακτήρας δεν πρέπει να είναι ψηφίο.

 

Η Εντολή IMPLICIT NONE

Είδαμε στην προηγούμενη παράγραφο ότι μια σύμβαση που έχει παραμείνει από τις παλαιότερες εκδόσεις της Fortran είναι ότι όλες οι μεταβλητές που αρχίζουν από τα γράμματα Ι – Ν είναι ακέραιες ενώ όλες οι υπόλοιπες είναι πραγματικές.

Αυτή η σύμβαση παύει να ισχύει αν χρησιμοποιήσουμε εντολές δήλωσης, όπως είναι οι INTEGER, REAL, LOGICAL, COMPLEX κ.ά. Στην Fortran 90 μπορούμε να ακυρώσουμε την παραπάνω σύμβαση αν χρησιμοποιήσουμε την εντολή IMPLICIT NONE και ανάλογες εντολές δήλωσης, όπως παρακάτω :

IMPLICIT NONE

INTEGER::A=0

REAL::I, J

REAL::A1=1.5, A2 = 3.4

Βλέπουμε ότι παράλληλα με τη δήλωση του τύπου μιας μεταβλητής μπορούμε να της δώσουμε και αρχική τιμή.

 

Οι Αριθμητικές Παραστάσεις στη Fortran

Οι αριθμητικές παραστάσεις στην Fortran μπορούν να αποτελούνται από μια απλή μεταβλητή ή και από μια πολύπλοκη αλγεβρική παράσταση. Τα σύμβολα που χρησιμοποιούμε και οι πράξεις που μπορούμε να κάνουμε μέσα στις αριθμητικές παραστάσεις είναι τα εξής :

Η ιεραρχία των αριθμητικών πράξεων μέσα σε μια αριθμητική παράσταση είναι η εξής : πρώτα υπολογίζονται οι δυνάμεις, μετά οι πολλαπλασιασμοί και οι διαιρέσεις και τέλος οι προσθέσεις και οι αφαιρέσεις. Για τις ισοδύναμες αριθμητικές πράξεις, η ιεραρχία είναι από αριστερά προς τα δεξιά. Βέβαια, αν χρησιμοποιηθούν παρενθέσεις, θα γίνουν πρώτα οι πράξεις μέσα στις παρενθέσεις.

Όταν γίνεται διαίρεση δύο ακεραίων αριθμών, τότε στην ουσία παίρνουμε το πηλίκο της ακέραιης διαίρεσης. Για παράδειγμα, το αποτέλεσμα της διαίρεσης 5/3 είναι 1 και το αποτέλεσμα της διαίρεσης 18/4 είναι 4.

 

Οι Ενσωματωμένες Συναρτήσεις της Fortran

Η Fortran είναι εφοδιασμένη με πάρα πολλές έτοιμες (ενσωματωμένες) συναρτήσεις, τις οποίες μπορούμε να καλούμε όποτε θέλουμε στα προγράμματά μας. Οι πιο χρήσιμες από τις συναρτήσεις αυτές είναι οι εξής :

Συνάρτηση

Αντίστοιχη

Μαθηματική

Τύπος των

Ορισμάτων

Τύπος του

Αποτελέσματος

Παρατηρήσεις

SIN(X)

ημ(Χ)

R

R

Το Χ σε ακτίνια

COS(X)

συν(Χ)

R

R

Το Χ σε ακτίνια

TAN(X)

εφ(Χ)

R

R

Το Χ σε ακτίνια

COTAN(X)

σφ(Χ)

R

R

Το Χ σε ακτίνια

ASIN(X)

τοξημ(Χ)

R

R

 <= 1

ACOS(X)

τοξσυν(Χ)

R

R

 <= 1

ATAN(X)

τοξεφ(Χ)

R

R

 

SQRT(X)

R

R

 

EXP(X)

eX

R

R

 

ALOG10(X)

log(X)

R

R

Δεκαδικός

λογάριθμος

LOG(X)

ln(X)

R

R

Νεπέρειος

λογάριθμος

CEILING(X)

Ο μικρότερος ακέραιος

που είναι >= Χ

R

I

 

FLOOR(X)

Ο μεγαλύτερος ακέραιος

που είναι <= Χ

R

I

 

ABS(X)

IABS(X)

R

I

R

I

 

FLOAT(X)

Μετατροπή ακεραίου

σε πραγματικό

I

R

 

IFIX(X)

Μετατροπή πραγματικού

σε ακέραιο

R

I

 

DBLE(X)

Μετατροπή αριθμού

σε διπλής ακρίβειας

R, I, C

D

 

SNGL(X)

Μετατροπή διπλής ακρίβειας

σε πραγματικό

D

R

 

SIGN(X1, X2)

ISIGN(X1, X2)

Συνάρτηση

πρόσημο

R

I

R

I

Απόλυτη τιμή του Χ1 επί

πρόσημο του Χ2

DIM(X1, X2)

IDIM(X1, X2)

Θετική διαφορά

R

I

R

I

Ίσο με Χ1-Χ2 αν Χ1>Χ2 και ίσο με 0 αν Χ1<=Χ2

REAL(X)

Μετατροπή ακεραίου

σε πραγματικό ή

το πραγματικό

μέρος μιγαδικού

C, I

R

 

AIMAG(X)

Φανταστικό μέρος

μιγαδικού

C

R

 

CONJG(X)

Συζυγής μιγαδικού

C

C

 

CMPLX(X1, X2)

Μετατροπή ακεραίων ή

πραγματικών σε μιγαδικό

R, I

C

=X1+jX2

MAX(X1, X2 …)

Μέγιστος

R

R

 

MIN(X1, X2 …)

Ελάχιστος

R

R

 

MOD(X1, X2)

Υπόλοιπο

διαίρεσης

I

I

 

AINT(X)

INT(X)

Αποκοπή δεκαδικού μέρους

R

R

R

I

 

ANINT(X)

NINT(X)

Στρογγυλοποίηση

R

R

R

I

 

CHAR(X)

Χαρακτήρας ASCII

I

CHAR

 

ICHAR(X)

Θέση χαρακτήρα

στον κώδικα ASCII

CHAR

I

 

LEN(X)

Πλήθος χαρακτήρων

CHAR

I

 

INDEX(X1, X2)

Θέση αλφαριθμητικού

μέσα σε άλλο

CHAR

I

Θέση όπου

ξεκινάει το Χ2

μέσα στο Χ1

LLT(X1, X2)

Σύγκριση αλφαριθμητικών (<)

CHAR

L

 

LGT(X1, X2)

Σύγκριση αλφαριθμητικών (>)

CHAR

L

 

LLE(X1, X2)

Σύγκριση αλφαριθμητικών (<=)

CHAR

L

 

LGE(X1, X2)

Σύγκριση αλφαριθμητικών (>=)

CHAR

L

 

            Ακολουθούν παραδείγματα :

FLOAT(12) = 12.                 ! Μετατροπή ακεραίου αριθμού σε πραγματικό

IFIX(16.87) = 16                  ! Μετατροπή πραγματικού αριθμού σε ακέραιο

DBLE(13.14) = 13.14D1                 ! Μετατροπή αριθμού σε διπλής ακρίβειας

SNGL(9.14D2) = 9.14E2     ! Μετατροπή διπλής ακρίβειας σε πραγματικό

SIGN(10, -5) = -10                           ! Χρήση της συνάρτησης πρόσημο

IDIM(10, 15) = 0                              ! Θετική διαφορά

REAL(10.3+3.4i) = 10.3                 ! Πραγματικό μέρος μιγαδικού αριθμού

AIMAG(10.3+3.4i) = 3.4                ! Φανταστικό μέρος μιγαδικού αριθμού

CONJG(10.3+3.4i) = 10.3–3.4i                   ! Συζυγής μιγαδικού αριθμού

CMPLX(-9.1, 35.34) = -9.1+35.34i            ! Δημιουργία μιγαδικού αριθμού

AINT(7.4) = 7.0                                ! Αποκοπή δεκαδικού μέρους

INT(7.4) = 7                                      ! Αποκοπή δεκαδικού μέρους

ANINT(7.8) = 8.0                             ! Στρογγυλοποίηση αριθμού

NINT(7.8) = 8                                   ! Στρογγυλοποίηση αριθμού

MAX(10.3, 31.4, 15.7) = 31.4           ! Υπολογισμός μεγίστου

MIN(10.3, 31.4, 15.7) = 10.3            ! Υπολογισμός ελαχίστου

MOD(18, 4) = 2                                ! Υπόλοιπο ακέραιης διαίρεσης

CHAR(65) =’A’                    ! Επιστροφή χαρακτήρα από τον κωδικό ASCII

ICHAR(‘A’) = 65                  ! Επιστροφή κωδικού ASCII από τον χαρακτήρα

LEN(‘FLORINA’) = 8                     ! Πλήθος χαρακτήρων αλφαριθμητικού

INDEX(‘FLORINA’, ‘O’) = 3         ! Θέση του 2ου ορίσματος

LLT(‘A’, ‘B’) = .TRUE.

LGT(‘C’, ‘D’) = .FALSE.

LLE(‘A’, ‘B’) = .TRUE.

LGE(‘C’, ‘D’) = .FALSE. 

 

Πράξεις με Αλφαριθμητικές Μεταβλητές

Ο τελεστής // ενώνει τα περιεχόμενα δύο αλφαριθμητικών μεταβλητών. Ακολουθούν παραδείγματα :

            CHARACTER*15::A, B*8, C*7

            B = ’ΦΛΩΡΙΝΑ’

            C = ‘ΚΟΖΑΝΗ’

            A = B // C

            A = B // ‘KAI ’ // C

Η μεταβλητή Α θα περιέχει αρχικά την τιμή ‘ΦΛΩΡΙΝΑ ΚΟΖΑΝΗ ’ και μετά την τιμή ‘ΦΛΩΡΙΝΑ ΚΑΙ ΚΟΖ’.

Μπορούμε να αποσπάσουμε χαρακτήρες από μια αλφαριθμητική μεταβλητή, ορίζοντας μέσα σε παρενθέσεις το κατώτερο και το ανώτερο όριο και χωρίζοντάς τα με τον χαρακτήρα :.

Για παράδειγμα, ο συμβολισμός Α(3:5) ορίζει ένα υποσύνολο της αλφαριθμητικής μεταβλητής Α που αποτελείται από τον τρίτο μέχρι και τον πέμπτο χαρακτήρα της.

Μπορούμε να παραλείψουμε το 1 σαν κατώτερο όριο. Για παράδειγμα, ο συμβολισμός Α(:5) είναι ίδιος με τον Α(1:5). Μπορούμε να παραλείψουμε και το ανώτερο όριο αν είναι ίσο με το πλήθος των χαρακτήρων της αλφαριθμητικής μεταβλητής. Για παράδειγμα, ο συμβολισμός Α(4:) είναι ίδιος με τον Α(4:10), αν φυσικά η αλφαριθμητική μεταβλητή Α αποτελείται από 10 χαρακτήρες.

Ο παραπάνω συμβολισμός μπορεί να χρησιμοποιηθεί και σε εντολές αντικατάστασης. Για παράδειγμα, η παρακάτω έκφραση :

            A(2:5) = B(4:7)

αντικαθιστά 3 χαρακτήρες της μεταβλητής Α με άλλους τρεις χαρακτήρες της μεταβλητής Β ενώ οι υπόλοιποι χαρακτήρες της μεταβλητής Α δεν επηρεάζονται.

 

Η Εντολή PARAMETER

Με την εντολή PARAMETER μπορούμε να δώσουμε τιμές σε κάποιες μεταβλητές ταυτόχρονα με τον ορισμό τους, οι οποίες όμως δεν θα μπορούν να αλλαχθούν στη συνέχεια. Πρόκειται στην ουσία για σταθερές με όνομα.

            Για παράδειγμα, η επόμενη εντολή :

            REAL, PARAMETER::PI=3.1415926

ορίζει μια πραγματική μεταβλητή με όνομα PI και με τιμή 3.1415926, η οποία δεν θα μπορεί να μεταβληθεί κατά την εκτέλεση του προγράμματος.

Μπορούμε να χρησιμοποιήσουμε και μόνη της την εντολή PARAMETER και με διάφορες μορφές, ως εξής :

            REAL(4)::PI, PI1

            CHARACTER::A*10, B*10

            PARAMETER(PI=3.1415926, PI1=PI/2)

            PARAMETER(A=’FLORINA’, B=’PER SEMPRE’)

 

Η Εντολή Εισόδου READ

Τα δεδομένα εισόδου σ’ ένα πρόγραμμα μπορούν να δοθούν από το πληκτρολόγιο με καταχωρήσεις του χρήστη ή και να διαβασθούν από ένα αρχείο. Η εντολή που χρησιμοποιούμε για να διαβάσουμε δεδομένα είναι η READ, η οποία έχει δύο μορφές σύνταξης :

            READ(u, f) list

ή

            READ f, list

Το u (unit) είναι ο κωδικός που χαρακτηρίζει τη μονάδα εισόδου. Μπορεί να συσχετιστεί με κάποιο αρχείο μέσω της εντολής OPEN, που θα την δούμε αργότερα, και η τιμή του πρέπει να είναι ακέραιη και μεταξύ των –32767 και 32767.

Για το πληκτρολόγιο χρησιμοποιούμε τις τιμές 0, 5 και το *, ενώ αν παραλείψουμε την τιμή του u, όπως στον δεύτερο τρόπο σύνταξης, τότε ως μονάδα εισόδου θεωρείται το πληκτρολόγιο.

Το f είναι ο αριθμός μιας εντολής FORMAT, η οποία καθορίζει τη μορφοποίηση των δεδομένων εισόδου και θα πρέπει να βρίσκεται κάπου μέσα στο πρόγραμμα. Αν στη θέση του f υπάρχει ο χαρακτήρας *, τότε μιλάμε για ελεύθερο FORMAT, δηλ. θα πρέπει οι τιμές των δεδομένων εισόδου να διαχωρίζονται μεταξύ τους με κόμμα ή με κενό.

Το list είναι μια σειρά μεταβλητών που διαχωρίζονται μεταξύ τους με κόμματα.

Σε γενικές γραμμές, η εντολή READ διαβάζει τις μεταβλητές που υπάρχουν στη list από τη μονάδα εισόδου που αντιστοιχεί στον αριθμό u και σύμφωνα με τις προδιαγραφές που υπάρχουν στην εντολή FORMAT στον αριθμό εντολής f.

            Ακολουθούν παραδείγματα :

            READ(5, *) A, B

            READ(*, *) I, BATHMOS

            READ *, C

            READ(5, 10) A, B

            10 FORMAT(2F8.2)

Στα παραδείγματα αυτά η είσοδος των τιμών των μεταβλητών γίνεται από το πληκτρολόγιο με καταχώρηση των τιμών από τον χρήστη κατά τη διάρκεια της εκτέλεσης του προγράμματος.

Μπορεί, όμως, οι τιμές των μεταβλητών να υπάρχουν ήδη αποθηκευμένες σε κάποιο αρχείο και να τις διαβάσουμε από εκεί όταν εκτελεσθεί το πρόγραμμα.

            Ακολουθούν παραδείγματα :

            OPEN(UNIT=10, FILE=’DATA’)

            READ(10, *) A1, A2

Η εντολή OPEN ανοίγει ένα αρχείο με όνομα DATA, το οποίο συσχετίζεται με τον αριθμό μονάδας 10, από το οποίο αρχείο γίνεται και το διάβασμα των τιμών των μεταβλητών Α1 και Α2 με ελεύθερο FORMAT.

            OPEN(UNIT=10, FILE=’DATA1’)

            READ(10, 20) A1, A2

            20 FORMAT (F5.2, F6.3)

Στο παράδειγμα αυτό δεν έχουμε ελεύθερο FORMAT.

 

Οι Εντολές Εξόδου WRITE και PRINT

Τα δεδομένα εξόδου σ’ ένα πρόγραμμα μπορούν να σταλούν απευθείας στην οθόνη ή και να γραφούν σ’ ένα αρχείο. Οι εντολές που χρησιμοποιούμε για να γράψουμε δεδομένα είναι η WRITE και η PRINT, οι οποίες έχουν την εξής σύνταξη :

            WRITE(u, f) list

και

            PRINT f, list

Το u (unit) είναι ο κωδικός που χαρακτηρίζει τη μονάδα εξόδου. Μπορεί να συσχετιστεί με κάποιο αρχείο μέσω της εντολής OPEN και η τιμή του πρέπει να είναι ακέραιη και μεταξύ των –32767 και 32767.

Για την οθόνη χρησιμοποιούμε τις τιμές 0, 6 και το *, ενώ αν παραλείψουμε την τιμή του u, όπως στον δεύτερο τρόπο σύνταξης, τότε ως μονάδα εξόδου θεωρείται η οθόνη.

Το f είναι ο αριθμός μιας εντολής FORMAT, η οποία καθορίζει τη μορφοποίηση των δεδομένων εξόδου και θα πρέπει να βρίσκεται κάπου μέσα στο πρόγραμμα. Αν στη θέση του f υπάρχει ο χαρακτήρας *, τότε μιλάμε για ελεύθερο FORMAT, δηλ. η μορφή εμφάνισης θα είναι η προκαθορισμένη από τον Η/Υ.

Το list είναι μια σειρά μεταβλητών που διαχωρίζονται μεταξύ τους με κόμματα.

Σε γενικές γραμμές, η εντολή εξόδου εμφανίζει (εξάγει) τις μεταβλητές που υπάρχουν στη list προς τη μονάδα εξόδου που αντιστοιχεί στον αριθμό u και σύμφωνα με τις προδιαγραφές που υπάρχουν στην εντολή FORMAT στον αριθμό εντολής f.

             Ακολουθούν παραδείγματα :

            WRITE(*, *) A, B

            WRITE(6, *) I, BATHMOS

            PRINT *, A, B

WRITE(*, *) ‘Η Α ΕΧΕΙ ΤΙΜΗ : ‘, A

PRINT *, ‘Η Β ΕΧΕΙ ΤΙΜΗ : ‘, B

Στα παραδείγματα αυτά η έξοδος των τιμών των μεταβλητών γίνεται προς την οθόνη κατά τη διάρκεια της εκτέλεσης του προγράμματος.

Μπορεί, όμως, να θέλουμε οι τιμές των μεταβλητών να αποθηκευθούν σε κάποιο αρχείο για να μπορούμε να τις διαβάσουμε από εκεί αργότερα ή και με κάποιο άλλο πρόγραμμα.

            Ακολουθούν παραδείγματα :

            OPEN(UNIT=11, FILE=’OUT’)

            WRITE(11, *) A1, A2

Η εντολή OPEN ανοίγει (δημιουργεί) ένα αρχείο με όνομα OUT, το οποίο συσχετίζεται με τον αριθμό μονάδας 11, στο οποίο αρχείο γίνεται και η εγγραφή των τιμών των μεταβλητών Α1 και Α2 με ελεύθερο FORMAT.

            OPEN(UNIT=11, FILE=’OUT1’)

            WRITE(11, 20) A1, A2

            20 FORMAT (F5.2, F6.3)

Στο παράδειγμα αυτό δεν έχουμε ελεύθερο FORMAT. Την εντολή WRITE μπορούμε να την χρησιμοποιήσουμε και για να εμφανίσουμε ένα περιγραφικό μήνυμα όταν πρόκειται να διαβάσουμε κάτι με την εντολή READ, όπως :

WRITE(*, *) ‘ΔΩΣΤΕ ΤΟΝ ΒΑΘΜΟ : ‘

READ(*, *) BATHMOS

 

Η Εντολή Εισόδου για Σειριακά Αρχεία

Η εντολή εισόδου δεδομένων για σειριακά αρχεία που χρησιμοποιεί η Fortran έχει την εξής γενική μορφή :

READ([UNIT=]u, [FMT=f][,END=e][,ERR=er][,IOSTAT=int][,ADVANCE=C-expr][,EOR=eor]) list

            Οι παράμετροι που είναι μέσα σε αγκύλες [ ] είναι προαιρετικές και η επεξήγησή τους έχει ως εξής :

Ακολουθούν παραδείγματα :

            READ(UNIT=10, FMT=*, END=100, ERR=200, IOSTAT=I) A

            READ(9, 10) B

            READ(7, 20, ADVANCE=’NO’, EOR=100) C

 

Η Εντολή Εισόδου για Αρχεία Άμεσης Προσπέλασης

Η γενική μορφή της εντολής εισόδου για την ανάγνωση ενός αρχείου άμεσης προσπέλασης, η εύρεση δηλαδή μιας συγκεκριμένης εγγραφής (record), είναι η εξής :

             READ([UNIT=]u,[FMT=]f[, ERR=er][, IOSTAT=int][, REC=rc]) list

Η παράμετρος REC=rc είναι ο αύξων αριθμός της εγγραφής μέσα στο αρχείο. Η rc μπορεί να έχει μια σταθερή τιμή ή μια μεταβλητή ή και μια έκφραση, αλλά πάντα ακέραιη και θετική.

            Ακολουθούν παραδείγματα :

            READ(10, 100, REC=25) A, B

            READ(10, *, REC=I) A

 

Η Εντολή Εξόδου για Σειριακά Αρχεία

Η εντολή εξόδου δεδομένων που χρησιμοποιεί η Fortran για σειριακά αρχεία έχει την εξής γενική μορφή :

WRITE([UNIT=] u, [FMT=] f [, ERR=er][, IOSTAT=int] [, ADVANCE=C-expr]) list

Οι παράμετροι που χρησιμοποιούντα είναι ίδιες μ’ αυτές της εντολής εισόδου, ενώ οι παράμετροι END και EOR δεν έχουν νόημα εδώ.

            Ακολουθούν παραδείγματα :

            WRITE(UNIT=10, FMT=30, ERR=200, IOSTAT=I) A, B

            WRITE(10, 30) A

 

Η Εντολή Εξόδου για Αρχεία Άμεσης Προσπέλασης

Η γενική μορφή της εντολής εξόδου για τα αρχεία άμεσης προσπέλασης είναι η εξής :

             WRITE([UNIT=]u,[FMT=]f[, ERR=er][, IOSTAT=int], REC=rc) list

            Η παράμετρος REC=rc είναι ο αύξων αριθμός της εγγραφής μέσα το αρχείο. Η rc μπορεί να έχει μια σταθερή τιμή ή μια μεταβλητή ή και μια έκφραση, αλλά πάντα ακέραιη και θετική. Ακολουθούν παραδείγματα :

            WRITE(11, 80, ERR=100, REC=32) A, B

            READ(*, *) A

            WRITE(20, *, ERR=90, REC=I) A

            I = I + 1

 

Η Εντολή OPEN

Με την εντολή OPEN μπορούμε να ανοίξουμε ένα αρχείο για επεξεργασία (διάβασμα ή εγγραφή δεδομένων) και να το συνδέσουμε μ’ έναν ακέραιο αριθμό μονάδας.

Η γενική μορφή της εντολής OPEN είναι η εξής :

            OPEN([UNIT=]u[,ACCESS=acc][,BLANK=bl][,ERR=er] [,FILE=fi][,FORM=fo][,IOSTAT=int][,RECL=rl][,STATUS=st])

            Όπου οι παράμετροι σημαίνουν τα εξής :

Ακολουθούν παραδείγματα :

            OPEN(UNIT=10, FILE=’DATA01’, ACCESS=’SEQUENTIAL’,

BLANK=’NULL’, ERR=100, FORM=’FORMATTED’,

IOSTAT=I, STATUS=’UNKNOWN’)

            OPEN(20, ACCESS=’DIRECT’, STATUS=’NEW’, RECL=70)

 

Η Εντολή CLOSE

Τα αρχεία που έχουμε ανοίξει με την εντολή OPEN, θα κλείσουν αυτόματα με το τέλος της εκτέλεσης του προγράμματος. Αν, όμως, θέλουμε να κλείσουμε κάποιο ανοικτό αρχείο κατά τη διάρκεια της εκτέλεσης του προγράμματος, θα πρέπει να χρησιμοποιήσουμε την εντολή CLOSE, η οποία έχει την εξής σύνταξη :

            CLOSE([UNIT=]u[,ERR=er][,IOSTAT=int][,STATUS=st])

            Όπου οι παράμετροι σημαίνουν τα εξής :

Ακολουθούν παραδείγματα :

            CLOSE(10)

            CLOSE(20, ERR=100)

            CLOSE(10, ERR=200, IOSTAT=I, STATUS=’DELETE’)

 

Η Εντολή REWIND

Με την εντολή REWIND επαναφέρουμε την κεφαλή του δίσκου στην πρώτη εγγραφή ενός σειριακού αρχείου και έχει την εξής σύνταξη :

            REWIND([UNIT=]u[, ERR=er][, IOSTAT=int])

Ακολουθούν παραδείγματα :

            REWIND(10)

            REWIND 20

            REWIND A

            REWIND(20, ERR=100)

            REWIND(UNIT=10, ERR=200, IOSTAT=I)

 

Η Εντολή BACKSPACE

            Με την εντολή BACKSPACE επαναφέρουμε την κεφαλή του δίσκου στην προηγούμενη εγγραφή ενός σειριακού αρχείου και έχει την εξής σύνταξη :

            BACKSPACE([UNIT=]u[, ERR=er][, IOSTAT=int])

Ακολουθούν παραδείγματα :

            BACKSPACE(10)

            BACKSPACE 20

            BACKSPACE A

            BACKSPACE(20, ERR=100)

            BACKSPACE(UNIT=10, ERR=200, IOSTAT=I)

 

Η Εντολή ENDFILE

Όπως ήδη γνωρίζουμε, όταν τελειώνει η προσπέλαση σε κάποιο αρχείο, το πρόγραμμα τοποθετεί στο τέλος του αρχείου μια ειδική εγγραφή (end-of-file), η οποία δηλώνει το τέλος του αρχείου. Για να τοποθετήσουμε εμείς μια τέτοια εγγραφή και όχι αυτόματα το πρόγραμμα, πρέπει να χρησιμοποιήσουμε την εντολή ENDFILE, η οποία έχει την εξής σύνταξη :

            ENDFILE([UNIT=]u[, ERR=er][, IOSTAT=int])

Ακολουθούν παραδείγματα :

            ENDFILE(10)

            ENDFILE 20

            ENDFILE A

            ENDFILE (20, ERR=100)

            ENDFILE (UNIT=10, ERR=200, IOSTAT=I)

 

Η Εντολή GO TO Χωρίς Όρους

Η εντολή GO TO είναι η πρώτη από τις εντολές ελέγχου (control statements) που θα μελετήσουμε και η μορφή της εντολής χωρίς όρους (unconditional) μεταφέρει τον έλεγχο (τη ροή) του προγράμματος σε μια συγκεκριμένη εντολή. Η σύνταξή της είναι ως εξής :

            GO TO n

όπου το n είναι ο αριθμός μιας άλλης εντολής του προγράμματος.

            Ακολουθεί ένα παράδειγμα χρήσης της εντολής :

            ! Η ΕΝΤΟΛΗ GO TO ΧΩΡΙΣ ΟΡΟΥΣ

            I = 1

            SUM = 0

10          SUM = SUM + A

I = I + 1

            IF (I > 100) GO TO 20

            GO TO 10

   20     PRINT *, ‘ΑΘΡΟΙΣΜΑ=’, SUM

            STOP

            END

 

Το Υπολογισμένο GO TO

Η εντολή αυτή (computed GO TO), όπως και η προηγούμενη, είναι απομεινάρια από τις παλιές εκδόσεις της Fortran και εξακολουθούν να ισχύουν και να χρησιμοποιούνται ακόμα αν και η χρήση τους έχει ατονήσει με τις νέες σύγχρονες τεχνικές των νεώτερων εκδόσεων της Fortran, η οποία συμπορεύεται πλέον με τις άλλες, δομημένες γλώσσες προγραμματισμού.

Η σύνταξή της είναι ως εξής :

            GO TO (n1, n2, …, nm)[,]I

όπου τα n1, n2, … και nm είναι αριθμοί εντολών του προγράμματος και το Ι είναι μια ακέραιη σταθερή ή μεταβλητή με τιμές 1, 2, …, m, ώστε ανάλογα με την τιμή της να εκτελεσθεί αμέσως μετά η αντίστοιχη εντολή n1, n2, …, nm. Αν η τιμή του Ι είναι μεγαλύτερη από το m ή μικρότερη από το 1, τότε θα εκτελεσθεί η εντολή που ακολουθεί την GO TO.

            Ακολουθεί ένα παράδειγμα χρήσης της εντολής :

            A1 = 10

            A2 = 20

            GO TO (10, 20, 30, 40) I

10          S = A1 + A2

GO TO 50

20          S = A1 – A2

GO TO 50

30     S = A1 * A2

GO TO 50

   40     S = A1 / A2

   50 …

 

Η Δομή CASE

Η προηγούμενη εντολή θεωρείται κάπως ξεπερασμένη και στη θέση της χρησιμοποιείται πλέον η δομή CASE, η οποία έχει την εξής σύνταξη :

[name:] SELECT CASE (expr)

                        CASE (A1 [, A2] … ])[name]

                                    Block εντολών1

            CASE (B1 [, B2] … ])[name]

                                    Block εντολών2

            …

            [CASE DEFAULT [name]

Block εντολών3]

            END SELECT [name]

            Όπου έχουμε τα εξής :

Η δομή δουλεύει ως εξής : αν η τιμή της έκφρασης expr είναι μεταξύ των τιμών Α1, Α2 κοκ, θα εκτελεσθεί το block εντολών1, αν η τιμή της έκφρασης expr είναι μεταξύ των τιμών Β1, Β2 κοκ, θα εκτελεσθεί το block εντολών2, ενώ αν η τιμή της έκφρασης expr δεν βρεθεί πουθενά ανάμεσα στις προαναφερόμενες τιμές, τότε θα εκτελεσθεί το block εντολών3.

            Οι εκφράσεις που μπορούμε να χρησιμοποιήσουμε μέσα σε μια εντολή CASE είναι οι εξής :

Ακολουθούν παραδείγματα :

NAME1: SELECT CASE(I)

                        CASE(:– 4)

                        A=1

CASE(2)

                        A=2

CASE(–2:3)

                        A=3

            CASE DEFAULT

                        A=4

            END SELECT NAME1

Το παρακάτω παράδειγμα υπολογίζει τις ημέρες ενός μήνα αν δώσουμε σαν δεδομένα την αρίθμηση του μήνα στην αριθμητική μεταβλητή MONTH καθώς και το αν το έτος είναι δίσεκτο ή όχι στη λογική μεταβλητή DISEKTO.

SELECT CASE(MONTH)

            CASE(4, 6, 9, 11)

                        IMERES=30

CASE(1, 3, 5, 7:8, 10, 12)

                        IMERES=31

                        CASE(2)

                                    SELECT CASE(DISEKTO)

                                                CASE(.TRUE.)

                                                            IMERES=29

CASE(.FALSE.)

                                                            IMERES=28

                                    END SELECT

            END SELECT

Παρατηρούμε ότι έχουμε μια δομή CASE ένθετη μέσα σε μια άλλη δομή CASE καθώς και το ότι δεν χρησιμοποιήσαμε ονόματα για τις δομές.

 

Η Εντολή ASSIGN

Η εντολή ASSIGN ανήκει στις παλιές εντολές της Fortran και τελεί υπό κατάργηση στις καινούργιες εκδόσεις της γλώσσας. Μας δίνει τη δυνατότητα να αντιστοιχίσουμε μια ακέραιη μεταβλητή με τον αριθμό κάποιας εντολής του προγράμματος ή τον αριθμό κάποιας εντολής FORMAT.

Η σύνταξή της είναι ως εξής :

            ASSIGN αριθμός_εντολής TO ακέραιη_μεταβλητή

            Για παράδειγμα, με την εντολή :

            ASSIGN 100 TO I

η ακέραιη μεταβλητή I έχει τιμή 100 και μέσα στο πρόγραμμα θα πρέπει να υπάρχει κάποια εντολή με αριθμό 100. Την μεταβλητή I δεν θα μπορούμε να την χρησιμοποιήσουμε σε μια εντολή αντικατάστασης.

            Ακολουθεί ένα παράδειγμα :

           

            ASSIGN 10 TO I

            IF (K==1) GO TO I

            …

10          WRITE(*, *) ‘…’

   20     WRITE(*, *) ‘…’

            STOP

            END

 

Η Εντολή IF

Η γενική μορφή της εντολής IF είναι η εξής :

            IF(λογική_έκφραση) εκτελέσιμη_εντολή

Η εκτελέσιμη_εντολή δεν πρέπει να είναι μια εντολή DO ή ένα άλλο λογικό IF.

            Ακολουθούν μερικά χαρακτηριστικά παραδείγματα :

            IF(A>B) GO TO 100

            IF(C<D) DA = B * 10

            IF(X>0.) S = S + BATHMOS

            IF(A==B) GO TO 200

            IF(X/=Y) GO TO 300

            IF(A<=B) WRITE(6, 10) A

Οι τελεστές σύγκρισης των εκδόσεων 77 και 90 της Fortran είναι οι εξής :

Fortran 77

Fortran 90

Ερμηνεία

.GT.

>

Μεγαλύτερο

.LT.

<

Μικρότερο

.GE.

>=

Μεγαλύτερο ή ίσο

.EQ.

==

Ίσο

.NE.

/=

Όχι ίσο

.LE.

<=

Μικρότερο ή ίσο

Η Fortran χρησιμοποιεί και τους τρεις γνωστούς λογικούς τελεστές .AND., .OR. και .NOT.

            Ακολουθούν παραδείγματα :

            IF(A>B .AND. A>C) GO TO 100

            IF(I==1 .OR. J<10) GO TO 200

            IF(.NOT.(A>B)) A = A + 1

 

Το Αριθμητικό IF

Και η εντολή αυτή αποτελεί μια ανάμνηση από τις παλιές εκδόσεις της Fortran και τελεί υπό κατάργηση. Η γενική μορφή της είναι η εξής :

            IF(αριθμητική_έκφραση) εντολή1, εντολή2, εντολή3

Η εντολή δουλεύει ως εξής : αν το αποτέλεσμα της αριθμητικής_έκφρασης είναι αρνητικό θα εκτελεσθεί η εντολή1, αν είναι μηδέν θα εκτελεσθεί η εντολή2 και αν είναι θετικό θα εκτελεσθεί η εντολή3.

            Ακολουθούν παραδείγματα :

            IF(X) 10, 20, 30

            IF(A–B) 15, 15, 25

 

            SUM = 0

10          READ(%, *) X

IF(X) 10, 30, 20

20          SUM = SUM + X**2

GO TO 10

30          WRITE(6, *) SUM

END

 

Η Εντολή IF-THEN-ELSE

Η εντολή IF που είδαμε σε προηγούμενη παράγραφο αποτελεί την πιο απλή μορφή της δημοφιλούς αυτής εντολής. Έχει το βασικό μειονέκτημα ότι μας επιτρέπει να εκτελέσουμε μία μόνο εντολή αν κάποια λογική έκφραση είναι αληθής (TRUE).

Για να μπορέσουμε να εκτελέσουμε περισσότερες από μία εντολές ανάλογα με το αποτέλεσμα μιας λογικής έκφρασης, μπορούμε να χρησιμοποιήσουμε την εξής μορφή της εντολής IF :

            IF (λογική_έκφραση) THEN

            … εντολές …

            ENDIF

Αν η λογική_έκφραση είναι αληθής (TRUE) θα εκτελεσθούν οι εντολές που βρίσκονται μέσα στο μπλοκ IF … ENDIF, ενώ αν η λογική_έκφραση είναι ψευδής (FALSE) ο έλεγχος θα μεταφερθεί στην εντολή που βρίσκεται αμέσως μετά την εντολή ENDIF.

            Ακολουθεί ένα παράδειγμα :

            IF(A>B) THEN

                        SUM = SUM + A

                        P = P * B

             ENDIF

            Μπορούμε να έχουμε και ένθεση των εντολών IF, ως εξής :

            IF(A>10) THEN

                        IF(A>20) THEN

                                    SUM = SUM + A

                                    P = P * A

                        ENDIF

                        IF(A==20) THEN

                                    …

                        ENDIF

                        IF(A<20) THEN

                                    …

                        ENDIF

            ENDIF

Μπορούμε να βγούμε από την περιοχή των εντολών ενός IF πριν να εκτελεσθούν όλες οι εντολές του, με χρήση της εντολής GO TO, αλλά μπορούμε να στείλουμε τον έλεγχο του προγράμματος μόνο στην πρώτη εντολή του IF. 

            Ακολουθεί ένα παράδειγμα :

10          IF(A>B) THEN

READ(6, *) C

IF(C<0) GO TO 50

F = SQRT(C)

ENDIF

            …

50         

            GO TO 10

Για να μπορέσουμε να εκτελέσουμε κάποιες εντολές αν το αποτέλεσμα μιας λογικής έκφρασης είναι αληθές (TRUE) και κάποιες άλλες εντολές αν το αποτέλεσμα της ίδιας λογικής έκφρασης είναι ψευδές (FALSE), μπορούμε να χρησιμοποιήσουμε και την εντολή ELSE, ως εξής :

            IF (λογική_έκφραση) THEN

            … εντολές αν η λογική_έκφραση είναι TRUE …

ELSE

            … εντολές αν η λογική_έκφραση είναι FALSE …

            ENDIF

Αν η λογική_έκφραση είναι αληθής (TRUE) θα εκτελεσθούν οι εντολές που βρίσκονται αμέσως μετά την εντολή IF … THEN, ενώ αν η λογική_έκφραση είναι ψευδής (FALSE) θα εκτελεσθούν οι εντολές που βρίσκονται αμέσως μετά την εντολή ELSE.

            Ακολουθεί ένα παράδειγμα :

            IF(A>0) THEN

                        SUM = SUM + A

            ELSE

                        P = P * A

            ENDIF

Υπάρχει η δυνατότητα να χρησιμοποιήσουμε και την εντολή ELSEIF για επιπλέον επιλογές, ως εξής :

            IF (λογική_έκφραση1) THEN

            … εντολές αν η λογική_έκφραση1 είναι TRUE …

ELSEIF(λογική_έκφραση2) THEN

… εντολές αν η λογική_έκφραση1 είναι FALSE

και η λογική_έκφραση2 είναι TRUE …

ELSE

            … εντολές αν η λογική_έκφραση1 και η λογική_έκφραση2

είναι FALSE …

            ENDIF

 

Οι Εντολές STOP και END

Η εντολή END αποτελεί την τελευταία εντολή κάθε προγράμματος και τερματίζει την εκτέλεσή του. Αν χρησιμοποιηθεί στα υποπρογράμματα θα έχει το ίδιο αποτέλεσμα με την εντολή RETURN. Είναι καλό, αν και είναι προαιρετικό, να γράφουμε τη δεσμευμένη λέξη PROGRAM και το όνομα του προγράμματος μετά από την εντολή END.

            Η σύνταξη της εντολής END είναι η εξής :

            END [PROGRAM [όνομα_προγράμματος]]

END [FUNCTION [όνομα_υποπρογράμματος]]

END [SUBROUTINE [όνομα_υποπρογράμματος]]

END [MODULE [όνομα_MODULE]]

END [BLOCK DATA [όνομα_BLOCK DATA]]

Ενώ χρησιμοποιούμε μία φορά την εντολή END για να τερματίσουμε ένα πρόγραμμα όταν αυτό φθάσει στο τέλος του, μπορούμε να χρησιμοποιήσουμε πολλές φορές μέσα σ’ ένα πρόγραμμα την εντολή STOP για να διακόψουμε εσκεμμένα την εκτέλεση ενός προγράμματος, εμφανίζοντας ταυτόχρονα κι ένα προαιρετικό μήνυμα.

            Η σύνταξη της εντολής STOP είναι η εξής :

            STOP [μήνυμα] | [ακέραιη_τιμή]

Το μήνυμα είναι μια αλφαριθμητική σταθερά και η ακέραια τιμή είναι ένας ακέραιος αριθμός μεγαλύτερος του 0. Το μήνυμα χρησιμοποιείται για να μπορέσουμε να καταλάβουμε σε ποιο σημείο του προγράμματος διακόπηκε η εκτέλεσή του και να μπορέσουμε έτσι να διερευνήσουμε τι δεν πήγε καλά.

            Ακολουθούν παραδείγματα :

            READ(*, *) A

            IF(A<0) STOP ‘ΟΧΙ ΑΡΝΗΤΙΚΕΣ ΤΙΜΕΣ’

            C = SQRT(A)

IF(C==2) STOP ‘ΟΧΙ ΤΟΣΟ ΕΥΚΟΛΕΣ ΤΙΜΕΣ’

STOP ‘ΕΔΩ ΤΕΛΕΙΩΝΕΙ ΚΑΝΟΝΙΚΑ ΤΟ ΠΡΟΓΡΑΜΜΑ’

END

 

Η Εντολή PAUSE

Είναι από τις παλιές εντολές της Fortran που τελούν υπό κατάργηση. Σ’ αντίθεση με την εντολή STOP, η οποία προκαλεί τερματισμό της εκτέλεσης του προγράμματος, η εντολή PAUSE προκαλεί μια προσωρινή διακοπή, εμφανίζει ένα προαιρετικό μήνυμα και περιμένει μια ενέργεια του χρήστη για να συνεχίσει την εκτέλεση του προγράμματος.

Η σύνταξη της εντολής PAUSE είναι η εξής :

            PAUSE [μήνυμα] | [ακέραιη_τιμή]

Το μήνυμα είναι μια αλφαριθμητική σταθερά και η ακέραια τιμή είναι ένας ακέραιος αριθμός μεγαλύτερος του 0. Το μήνυμα χρησιμοποιείται για να κάνει κάποια απαραίτητη ενέργεια ο χρήστης πριν συνεχισθεί η εκτέλεση του προγράμματος. Συνήθως πρέπει να πατήσουμε το πλήκτρο enter για να συνεχισθεί η εκτέλεση του προγράμματος.

            Ακολουθούν παραδείγματα :

            PAUSE

            PAUSE ‘ΠΡΕΠΕΙ ΝΑ ΑΛΛΑΞΕΤΕ ΧΑΡΤΙ ΣΤΟΝ ΕΚΤΥΠΩΤΗ’

PAUSE ‘ΤΟΠΟΘΕΤΗΣΤΕ ΜΙΑ ΔΙΣΚΕΤΑ ΣΤΟ DRIVE’

 

Η Εντολή DO

Η εντολή DO της Fortran αποτελεί την αντίστοιχη πολύ δημοφιλή εντολή FOR, γνωστή από άλλες γλώσσες προγραμματισμού.

Η σύνταξη της εντολής είναι ως εξής :

            [ΟΝΟΜΑ:] DO [n][,][var=start, stop, inc]

                        … εντολές …

            END DO

Όπου έχουμε τα εξής :

Η εντολή n αποκαλείται τελική εντολή, η μεταβλητή var αποκαλείται δείκτης της DO, η start αποκαλείται αρχική τιμή, η stop αποκαλείται τελική τιμή και η inc αποκαλείται βήμα ή αύξηση.

Ο βρόχος της εντολής DO τελειώνει με την εντολή END DO, αλλά αν στην εντολή DO υπάρχει ο αριθμός μιας εντολής n, τότε η τελευταία εντολή του βρόχου θα πρέπει να έχει τον αριθμό n ή να είναι μια εντολή CONTINUE με τον αριθμό n. Αν στην εντολή DO έχουμε δώσει και όνομα, τότε το ίδιο όνομα θα πρέπει να υπάρχει και στην εντολή END DO.

Συνεπώς, οι μορφές που μπορεί να πάρει η εντολή DO είναι οι εξής τρεις :

            [ΟΝΟΜΑ:] DO var=start, stop, inc

                        … εντολές …

            END DO [ONOMA]

ή

            [ΟΝΟΜΑ:] DO

                        … εντολές …

            END DO [ONOMA]

ή

            DO n var=start, stop, inc

                        … εντολές …

            n τελική_εντολή

ή

            n CONTINUE

Αναφορικά με την πρώτη μορφή της εντολής DO, η όλη διαδικασία θυμίζει πολύ την γνωστή εντολή FOR από άλλες γλώσσες προγραμματισμού. Δηλαδή, η μεταβλητή var ξεκινά με την τιμή start και εκτελούνται όλες οι εντολές που βρίσκονται ανάμεσα στις εντολές DO και END DO.

Μετά, η μεταβλητή var αυξάνεται κατά την τιμή της inc και εκτελούνται ξανά οι ίδιες εντολές κοκ. Μόλις η τιμή της var ξεπεράσει την τιμή της stop, η εκτέλεση του προγράμματος συνεχίζεται με την εντολή που βρίσκεται αμέσως μετά την εντολή END DO.

Όταν το βήμα έχει την τιμή 1 και η var είναι ακέραιη μεταβλητή, τότε μπορεί να παραληφθεί.

            Ακολουθούν παραδείγματα :

            DO I=1, 100, 1

            DO I=6, 80, 2

            DO I=3.1, 97.3, 0.6

            DO J=–10, 60, 2

            DO J=100, 10, –2

 

            SUM = 0

            DO I=1, 100, 1

                        SUM = SUM + I

            END DO

ή

            SUM = 0

            P1:DO I=1, 100, 1

                        SUM = SUM + I

            END DO P1

Σύμφωνα με τη δεύτερη μορφή της εντολής DO, οι εντολές του βρόχου εκτελούνται συνέχεια μέχρι κάποια εντολή του βρόχου να στείλει τη ροή του προγράμματος έξω από τον βρόχο.

            Ακολουθεί ένα παράδειγμα :

            I = 1

            SUM = 0

            DO

                        SUM = SUM + I

                        IF(SUM>1000) THEN

                                    WRITE(*, *) ‘I = ‘, I

                                    STOP

                        END IF

                        I = I + 1

            END DO

 Χρήσιμες στη δεύτερη μορφή της εντολής DO είναι οι εντολές EXIT και CYCLE. Η πρώτη προκαλεί έξοδο από τον βρόχο, ενώ η δεύτερη στέλνει τη ροή του προγράμματος στην αρχή του βρόχου.

Αν η εντολή EXIT ακολουθείται από το όνομα ενός βρόχου DO, τότε προκαλείται έξοδος από τον βρόχο αυτό και απ’ όλους τους βρόχους που περιέχει.

Η εντολή CYCLE διακόπτει την τρέχουσα επανάληψη του βρόχου, η μεταβλητή var αυξάνει σύμφωνα με το βήμα και ξεκινάει μια καινούργια επανάληψη. Αν η εντολή CYCLE ακολουθείται από το όνομα ενός βρόχου DO, τότε προκαλείται έξοδος απ’ όλους τους βρόχους που περιέχει ο τρέχον βρόχος και η ροή του προγράμματος πηγαίνει στον βρόχο που έχουμε καθορίσει με το όνομά του.

            Ακολουθούν παραδείγματα :

            LOOP1:DO I=1, 50

                        A=A+2

                        IF(A>20) EXIT LOOP1

            END DO LOOP1

 

            SUM = 0

            M = 0

            DO

                        READ(*, *) A

                        IF(A<0) EXIT

                        SUM = SUM + A

                        M= M + 1

            END DO

            WRITE(*, *) SUM/M

 

            I = 0

            DO

                        READ(*, *) A

                        IF(A<0) THEN

EXIT

                        ELSEIF(MOD(A, 2)==1) THEN

                                    CYCLE

                        ELSE

                                    I = I + 1

                        END IF

            END DO

            WRITE(*, *) ‘ΠΛΗΘΟΣ ΑΡΤΙΩΝ ΑΡΙΘΜΩΝ : ‘, I

Η τρίτη μορφή της εντολής DO τελεί υπό κατάργηση αλλά γίνεται ακόμα αποδεκτή. Χαρακτηριστικό παράδειγμα είναι το εξής :

            DO 10 I=1, 10

                        K = I * I

   10     WRITE(*, *) I, K

Σαν τελευταία εντολή ενός DO μπορούμε να χρησιμοποιήσουμε και την εντολή CONTINUE, ως εξής :

            DO 10 I=1, 10

                        …

                        DO 10 J=I, 20

                        …

10          CONTINUE

ή και ως εξής :

            DO 10 I=1, 10

                        …

                        DO 20 J=I, 20

                        …

               20     CONTINUE

                        …

   10     CONTINUE

 

Η Εντολή FORMAT

Με την εντολή FORMAT μπορούμε να ορίσουμε με ακρίβεια τη μορφή των δεδομένων του προγράμματος για είσοδο αλλά και για έξοδο.

Η γενική μορφή της εντολής είναι η εξής :

             f FORMAT(K1, K2, … Km)

όπου f είναι ο αριθμός της εντολής και τα Κ1, Κ2, … Km είναι ειδικές κωδικοποιήσεις της εντολής που θα δούμε αναλυτικά παρακάτω.

Μια εντολή FORMAT δεν είναι εκτελέσιμη εντολή και έτσι δεν έχει καμία σημασία σε ποια θέση θα την τοποθετήσουμε στο πρόγραμμα. Το πιο σωστό είναι να την τοποθετούμε μετά από την αντίστοιχη εντολή εισόδου ή εξόδου που αναφέρεται σ’ αυτήν αλλά μπορούμε και να τοποθετήσουμε όλες μαζί τις εντολές FORMAT ενός προγράμματος στην αρχή ή και στο τέλος του προγράμματος.

Πρέπει να έχουμε υπόψη μας ότι αν χρησιμοποιήσουμε μια εντολή FORMAT για να στείλουμε αποτελέσματα στον εκτυπωτή, τότε ο πρώτος χαρακτήρας θεωρείται χαρακτήρας ελέγχου και δεν εκτυπώνεται αλλά χρησιμοποιείται ως εξής :

 

Η Εντολή FORMAT με Πραγματικούς Αριθμούς

Για τη μορφοποίηση της εισόδου και της εξόδου των πραγματικών αριθμών με την εντολή FORMAT χρησιμοποιούμε τους κώδικες F και E.

Η σύνταξη του κώδικα F είναι η εξής :

            Fw.d

όπου το w είναι ένας ακέραιος αριθμός που καθορίζει το συνολικό πλάτος του πεδίου, δηλ. το πλήθος των ψηφίων συν την υποδιαστολή, και το d είναι ένας ακέραιος αριθμός που καθορίζει το πλήθος των δεκαδικών ψηφίων του αριθμού.

            Ακολουθούν παραδείγματα :

            READ(5, 10) A1, A2, A3

10          FORMAT(F8.3, F7.4, F10.2)

            WRITE(6, 20) A1, A2, A3

20     FORMAT(F10.4, F8.3, F5.2)

Ο κώδικας Ε χρησιμοποιείται για την είσοδο και έξοδο πραγματικών αριθμών σε εκθετική μορφή και η σύνταξή του είναι ως εξής :

            Ew.d[Ee]

όπου το w είναι ένας ακέραιος αριθμός που καθορίζει το συνολικό πλάτος του πεδίου, δηλ. το πλήθος των ψηφίων συν την υποδιαστολή, και το d είναι ένας ακέραιος αριθμός που καθορίζει το πλήθος των δεκαδικών ψηφίων του αριθμού.

Το e που υπάρχει μέσα στην αγκύλη είναι προαιρετικό και καθορίζει μόνο κατά την έξοδο το πλήθος των ψηφίων του εκθετικού μέρους του αριθμού.

            Ακολουθεί ένα παράδειγμα :

            WRITE(6, 30) A1, A2, A3

30     FORMAT(Ε13.4E3, Ε11.3, Ε12.2)

 

Η Εντολή FORMAT με Ακέραιους Αριθμούς

Για τη μορφοποίηση της εισόδου και της εξόδου των ακέραιων αριθμών με την εντολή FORMAT χρησιμοποιούμε τον κώδικα Ι, με την εξής σύνταξη :

            Iw[.m]

όπου το w είναι ένας ακέραιος αριθμός που καθορίζει το πλάτος του πεδίου και το m είναι ένας ακέραιος αριθμός που είναι προαιρετικός και καθορίζει μόνο κατά την έξοδο το μέγιστο πλήθος των μηδενικών μπροστά από τον αριθμό, αν χρειαστεί φυσικά να εμφανιστούν μηδενικά.

            Ακολουθούν παραδείγματα :

            READ(5, 10) I1, I2, I3

   10     FORMAT(I8, I7, I5)

            WRITE(6, 20) I1, I2, I3

20     FORMAT(I5, I6, I8.3)

 

Η Εντολή FORMAT με Αριθμούς Διπλής Ακρίβειας

Για τη μορφοποίηση της εισόδου και της εξόδου των αριθμών διπλής ακρίβειας με την εντολή FORMAT χρησιμοποιούμε τον κώδικα D, με την εξής σύνταξη :

            Dw.d

όπου το w είναι ένας ακέραιος αριθμός που καθορίζει το συνολικό πλάτος του πεδίου και το d είναι ένας ακέραιος αριθμός που καθορίζει τον αριθμό των δεκαδικών ψηφίων του αριθμού.

            Ακολουθεί ένα παράδειγμα :

            WRITE(6, 30) A1, A2, A3

30     FORMAT(D13.4, D11.3, D12.2)

 

Η Εντολή FORMAT με Λογικές Τιμές

Για τη μορφοποίηση της εισόδου και της εξόδου των τιμών των λογικών μεταβλητών με την εντολή FORMAT χρησιμοποιούμε τον κώδικα L, με την εξής σύνταξη :

            Lw

όπου το w είναι ένας ακέραιος αριθμός που καθορίζει το συνολικό πλάτος του πεδίου.

Κατά την είσοδο λογικών τιμών θα πρέπει να γράφουμε τα γράμματα T ή F ή ολόκληρα σαν .TRUE. και .FALSE. αντίστοιχα, ενώ κατά την έξοδο εμφανίζεται το γράμμα T ή F στη δεξιότερη θέση του πεδίου και οι υπόλοιπες θέσεις του πεδίου είναι κενές.

            Ακολουθούν παραδείγματα :

            LOGICAL L1, L2, L3

            READ(5, 10) L1, L2, L3

10     FORMAT(L1, L2, L5)

            WRITE(6, 20) L1, L2, L3

20     FORMAT(L3, L1, L2)

 

Η Εντολή FORMAT με Αλφαριθμητικές Τιμές

Για τη μορφοποίηση της εισόδου και της εξόδου των τιμών των αλφαριθμητικών μεταβλητών με την εντολή FORMAT χρησιμοποιούμε τον κώδικα Α, με την εξής σύνταξη :

            Αw

όπου το w είναι ένας ακέραιος αριθμός που καθορίζει το συνολικό πλάτος του πεδίου.

Αν οι χαρακτήρες της αλφαριθμητικής μεταβλητής που θα γράψουμε κατά την είσοδο είναι περισσότεροι από το μήκος της αλφαριθμητικής μεταβλητής όπως αυτό έχει ορισθεί με μια εντολή CHARACTER, τότε θα γίνει αποκοπή από τα αριστερά.

            Ακολουθεί ένα παράδειγμα :

            CHARACTER A*5

            READ(5, 10) A

10     FORMAT(A7)

Αν σύμφωνα με τις παραπάνω εντολές γράψουμε το κείμενο ‘FLORINA’, τότε στη μεταβλητή Α θα καταχωρηθούν οι χαρακτήρες ‘ORINA’.

Αν οι χαρακτήρες της αλφαριθμητικής μεταβλητής που θα γράψουμε κατά την είσοδο είναι λιγότεροι από το μήκος της αλφαριθμητικής μεταβλητής όπως αυτό έχει ορισθεί με μια εντολή CHARACTER, τότε θα προστεθούν κενά στα δεξιά της μεταβλητής.

            Ακολουθεί ένα παράδειγμα :

            CHARACTER A*10

            READ(5, 10) A

10     FORMAT(A7)

Αν σύμφωνα με τις παραπάνω εντολές γράψουμε το κείμενο ‘FLORINA’, τότε στη μεταβλητή Α θα καταχωρηθούν οι χαρακτήρες ‘FLORINAbbb’.

Κατά την έξοδο αλφαριθμητικών τιμών, αν το πλάτος του πεδίου είναι μεγαλύτερο από το μήκος της αλφαριθμητικής μεταβλητής, το κείμενο θα εμφανισθεί στοιχισμένο δεξιά μέσα στο οριζόμενο πεδίο, ενώ αν το πλάτος του πεδίου είναι μικρότερο από το μήκος της αλφαριθμητικής μεταβλητής θα αποκοπούν οι δεξιότεροι χαρακτήρες της αλφαριθμητικής μεταβλητής.

            Ακολουθεί ένα παράδειγμα :

            CHARACTER A*7

            A = ‘FLORINA’

            WRITE(6, 10) A

10     FORMAT(A5)

            Σύμφωνα με τις παραπάνω εντολές, θα εκτυπωθεί το κείμενο ‘FLORI’.

 

Ο Κώδικας Η της Εντολής FORMAT

Με τον κώδικα Η, που το όνομά του προέρχεται από τον γνωστό κατασκευαστή μηχανών υπολογισμού στα τέλη του 19ου αιώνα Hollerith, μπορούμε να εμφανίσουμε στην έξοδο μαζί με τα αποτελέσματα κάποια επιπλέον δικά μας μηνύματα.

Η μορφή του κώδικα Η είναι η εξής :

            nH

όπου n το είναι το πλήθος των χαρακτήρων που θα αποτελούν το μήνυμα.

Ακολουθεί ένα παράδειγμα :

            A1 = 10.41

            A2 = 5.32

            WRITE(6, 10) A1, A2

10          FORMAT(3HA1=, F5.2, 3HA2=, F4.2)

Το αποτέλεσμα θα είναι :

            A1=10.41A2=5.32

Μπορούμε αντί να χρησιμοποιούμε τον κώδικα Η και να αναγκαζόμαστε να μετράμε τους χαρακτήρες που θέλουμε να εμφανισθούν στην έξοδο, να χρησιμοποιήσουμε μονές αποστρόφους, ως εξής :

            A1 = 10.41

            A2 = 5.32

            WRITE(6, 10) A1, A2

   10     FORMAT(‘ ‘, ‘A1=’, F5.2, ‘A2=’, F4.2)

Το αποτέλεσμα θα είναι :

            A1=10.41A2=5.32

            WRITE(6, 10)

   20     FORMAT(‘ ‘, ‘  ΦΛΩΡΙΝΑ  ‘)

Το αποτέλεσμα θα είναι :

            ‘  ΦΛΩΡΙΝΑ  ‘

  

Ο Κώδικας Χ της Εντολής FORMAT

Με τον κώδικα Χ μπορούμε να πληροφορήσουμε τον Η/Υ κατά τη είσοδο δεδομένων να αγνοήσει κάποιους χαρακτήρες, ενώ κατά την έξοδο να εκτυπώσει κενούς χαρακτήρες.

Η μορφή του κώδικα Χ είναι η εξής :

           

όπου n το είναι το πλήθος των χαρακτήρων που θα αγνοηθούν κατά την είσοδο ή το πλήθος των κενών θέσεων κατά την έξοδο.

            Ακολουθούν παραδείγματα :

            READ(5, 10) A1, A2

   10     FORMAT(F5.2, 5X, F4.2)

            WRITE(6, 20) A1, A2

   20     FORMAT(3X, F5.2, 5X, F4.2)

 

Ο Κώδικας / της Εντολής FORMAT

Με τον κώδικα / μπορούμε να διακόψουμε κατά την είσοδο δεδομένων την προσπέλαση σε μια εγγραφή (record) και να πάμε στην επόμενη εγγραφή, ενώ κατά την έξοδο μπορούμε να διακόψουμε το γράψιμο σε μια εγγραφή και να πάμε στην επόμενη εγγραφή.

Η μορφή του κώδικα / είναι η εξής :

            n(/) ή //…/

όπου n το είναι το πλήθος των χαρακτήρων /.

            Ακολουθούν παραδείγματα :

            READ(5, 10) A1, A2

   10     FORMAT(F5.2//F4.2)

            WRITE(6, 20) A1, A2

   20     FORMAT(5X, ‘ΑΠΟΤΕΛΕΣΜΑΤΑ = ‘/3Χ, ‘Α1=’, F5.2/3Χ,’Α2=’, F4.2)

Θα πρέπει να έχουμε υπόψη μας ότι κατά την εκτύπωση των αποτελεσμάτων, το πρώτο κενό από τους χαρακτήρες Χ χρησιμοποιείται σαν χαρακτήρας ελέγχου και έτσι τα κενά που θα εκτυπωθούν με βάση την παραπάνω εντολή θα είναι 4, 2 και 2 και όχι 5, 3 και 3.

 

Ο Κώδικας \ της Εντολής FORMAT

Με τον κώδικα \ (backslash) μπορούμε να ορίσουμε την παραμονή του δρομέα (cursor) στην ίδια εγγραφή με το τέλος μιας εντολής READ ή WRITE και να μην αλλάζει έτσι εγγραφή.

            Ακολουθεί ένα παράδειγμα :

            WRITE(*, 10)

            READ(*, *) I

   10     FORMAT(10X, ‘ΔΩΣΕ ΤΗΝ ΤΙΜΗ ΤΟΥ I : ‘\)

 

Οι Κώδικες SP, SS και S της Εντολής FORMAT

Οι κώδικες αυτοί χρησιμοποιούνται για να ορίζουμε την εμφάνιση ή όχι του θετικού πρόσημου +, καθώς το αρνητικό πρόσημο – εμφανίζεται έτσι κι αλλιώς πάντοτε.

Ο κώδικας SP ορίζει την εμφάνιση του πρόσημου + μέχρι να συναντήσουμε έναν άλλον κώδικα, ο κώδικας SS καταργεί την εμφάνιση του πρόσημου + και ο κώδικας S επαναφέρει την προκαθορισμένη κατάσταση που ισχύει για το πρόσημο + των θετικών αριθμητικών τιμών.

            Ακολουθεί ένα παράδειγμα :

            A = 100

            WRITE(*, 10) A, A, A, A, A

10          FORMAT(10X, SP, I5, I5, SS, I5, SP, I5, S, I5)

 

Γενικοί Κανόνες για την Εντολή FORMAT

Σε περίπτωση που θέλουμε να χρησιμοποιήσουμε την ίδια ακριβώς μορφοποίηση για πολλές μεταβλητές, μπορούμε να χρησιμοποιήσουμε έναν αριθμό επανάληψης, ως εξής :

            READ(5, 10) A1, A2, A3, A4, A5

   10     FORMAT(3F5.2, 2F4.2)

Σύμφωνα με την παραπάνω εντολή FORMAT, οι τρεις πρώτες μεταβλητές θα διαβασθούν με τον κώδικα F5.2 και οι δύο επόμενες θα διαβασθούν με τον κώδικα F4.2.

Μπορούμε να χρησιμοποιήσουμε και παρενθέσεις για να επαναλάβουμε συνδυασμούς από κώδικες FORMAT, ως εξής :

            READ(5, 10) A1, A2, Ι1, Α3, Ι2

   10     FORMAT(F5.2, 2(F4.2, I5))

Μπορούμε να εκτυπώσουμε πολλούς ίδιους συνεχόμενους χαρακτήρες χρησιμοποιώντας έναν ακέραιο αριθμό και τους χαρακτήρες μέσα σε παρενθέσεις, ως εξής :

            WRITE(6, 20)

   20     FORMAT(5X, ‘ΑΠΟΤΕΛΕΣΜΑΤΑ = ‘/5Χ, 12(‘-‘))

            Σαν μια σύνοψη των κανόνων που ισχύουν για τις εντολές FORMAT, έχουμε τα εξής :

 

Οι Πίνακες (Arrays) στη Fortran

Οι πίνακες (arrays) ή μητρώα ή διατάξεις ή μεταβλητές με δείκτες είναι γνωστοί από άλλες γλώσσες προγραμματισμού για το πόσο χρήσιμοι είναι και το πόσο μεγάλη ευελιξία προσφέρουν στη συγγραφή των προγραμμάτων.

Για να μπούμε κατευθείαν στην έννοια των πινάκων στη Fortran, θα ξεκινήσουμε μ’ ένα απλό παράδειγμα ενός μονοδιάστατου πίνακα. Έστω ότι πρέπει να διαβάσουμε τις ποσότητες και τις τιμές από 10 προϊόντα και να υπολογίσουμε την αξία του κάθε προϊόντος καθώς και τη συνολική αξία όλων των προϊόντων.

            Γράφουμε το εξής πρόγραμμα :

DIMENSION POSO(10), TIMH(10), AXIA(10)

SYNOLO = 0

DO I=1, 10

            READ(*, *) POSO(I), TIMH(I)

            AXIA(I) = POSO(I) * TIMH(I)

            WRITE(*, *) AXIA(I)

            SYNOLO = SYNOLO + AXIA(I)

END DO

            WRITE(*, *) SYNOLO

            END

Ακολουθεί ένα παράδειγμα μ’ έναν πίνακα δύο διαστάσεων, με 20 γραμμές και 30 στήλες, όπου διαβάζουμε όλα τα στοιχεία (αριθμούς) του πίνακα και μετά υπολογίζουμε το άθροισμά τους καθώς και τον μέσο όρο τους.

            DIMENSION A(20, 30)

            SYNOLO = 0

            DO I = 1, 20

                        DO J = 1, 30

                                    READ(*, *) A(I, J)

                                    SYNOLO = SYNOLO + A(I, J)

                        END DO

            END DO

            MO = SYNOLO/600

Οι κανόνες που ισχύουν για τις μεταβλητές της Fortran ισχύουν και για τους πίνακες. Αυτό σημαίνει ότι αν το όνομα ενός πίνακα ξεκινάει μ’ έναν από τους χαρακτήρες I, J, K, L, M ή N, τότε όλα τα στοιχεία του πίνακα είναι ακέραιοι αριθμοί, αλλιώς είναι πραγματικοί αριθμοί.

Με τις κατάλληλες εντολές τύπου μπορεί ένας πίνακας να περιέχει διπλής ακρίβειας ή μιγαδικούς αριθμούς ή λογικές ή αλφαριθμητικές τιμές.

 

Η Εντολή DIMENSION

Με την εντολή DIMENSION δηλώνουμε τους πίνακες σ’ ένα πρόγραμμα Fortran και πιο συγκεκριμένα δηλώνουμε τα ονόματα των πινάκων που πρόκειται να χρησιμοποιήσουμε στο πρόγραμμα, τις διαστάσεις τους καθώς και τον συνολικό αριθμό των στοιχείων που θα περιέχει ο κάθε πίνακας.

Η γενική μορφή της εντολής DIMENSION είναι η εξής :

            DIMENSION[::]A1(l:m), A2(l :m), …, AN(l :m)

όπου έχουμε τα εξής :

Ακολουθούν παραδείγματα :

            DIMENSION::A(10, 20), B(100), IPOLISEIS(10, 15, 20)

Τα σύμβολα :: μπορούν να παραλειφθούν.

            DIMENSION::A(5:50, -10:20), K(-4:20, 100), M(19:36)

Στο παραπάνω παράδειγμα, οι τιμές των δεικτών των πινάκων δεν ξεκινούν από το 1, ως συνήθως, αλλά από άλλες τιμές, ακόμα και αρνητικές.

Μια άλλη πιο γενική μορφή της εντολής DIMENSION είναι η εξής :

            Type, DIMENSION(διαστάσεις)[::]A1[διαστάσεις] [, A2[διαστάσεις]]…

            όπου έχουμε τα εξής :

Ακολουθούν παραδείγματα :

            REAL, DIMENSION(100)::A, B, C(50)

INTEGER, DIMENSION(10, 10)::A1, A2, A3(20, 20)

CHARACTER(LEN=20), DIMENSION(50)::NAMES

Στο τελευταίο παράδειγμα ορίζουμε έναν μονοδιάστατο αλφαριθμητικό πίνακα που περιέχει 50 στοιχεία και με μέγιστο αριθμό χαρακτήρων 20 για το κάθε στοιχείο.

Πρέπει να έχουμε υπόψη μας ότι η εντολή DIMENSION είναι μη-εκτελέσιμη εντολή και πρέπει να την γράφουμε στην αρχή του προγράμματος. Ακόμη, όταν εκτελείται το πρόγραμμα θα πρέπει να έχουμε προνοήσει ώστε οι δείκτες των πινάκων που έχουμε ορίσει μέσα στο πρόγραμμα να μην ξεπερνάνε τα όρια που έχουμε καθορίσει.

 

Εργασία με Πίνακες

Εκτός από την κλασική εντολή DO που έχουμε χρησιμοποιήσει μέχρι τώρα για την καταχώρηση τιμών σ’ έναν πίνακα, υπάρχει και ένας πιο γρήγορος τρόπος καταχώρησης στοιχείων σε πίνακα με την εντολή READ, η λεγόμενη έμμεση εντολή DO (implied DO), που γράφεται ως εξής :

            READ(5, 10) (A(I), I=1, 10)

   10     FORMAT(10F5.2)

 

            READ(*, *) (A(I), I=1, 20)

            READ(5, *) (A(I), I=1, 30, 2)

 

            READ(5, 20) ((A(I, J), J=1, 20), I=1, 10)

   20     FORMAT(200F5.2)

 

            WRITE(6, 10) (A(I), I=1, 10)

   10     FORMAT(10F5.2)

 

            WRITE(6, 20) ((A(I, J), J=1, 20), I=1, 10)

20          FORMAT(200F5.2)

 

            WRITE(*, *) (A(I), I=1, 30, 2)

            Μπορούμε να χρησιμοποιήσουμε και μόνο το όνομα ενός πίνακα, αφού τον έχουμε ορίσει πρώτα με την εντολή DIMENSION, για να καταχωρήσουμε τιμές σ’ αυτόν, ως εξής :

            DIMENSION A(10)

            READ(5, 10) A

   10     FORMAT(10F5.2)

            Με τον παραπάνω τρόπο καταχώρησης τιμών σ’ έναν πίνακα, είμαστε υποχρεωμένοι να δώσουμε τιμές γι’ όλα τα στοιχεία του πίνακα, άρα θα πρέπει να γνωρίζουμε εκ των προτέρων το δηλωμένο μέγεθος του πίνακα.

            Στη Fortran 90 μπορούμε να κάνουμε ορισμένες πράξεις με τους πίνακες πολύ εύκολα, ενώ σε παλιότερες εκδόσεις της γλώσσας θα έπρεπε να γράψουμε αρκετές γραμμές κώδικα.

            Για παράδειγμα :

            DIMENSION (20)::A1, A2, A3, A4

            …

            A1 = A2

! ολόκληρος ο πίνακας Α2 καταχωρείται στον πίνακα Α1

Α3 = Α1 + Α2

! το άθροισμα των πινάκων Α1 και Α2 καταχωρείται στον πίνακα Α3

            Α4 = Α1 * 10

            ! ο πίνακας Α4 είναι ίσος με τον πίνακα Α1, όπου όμως όλα τα

! στοιχεία του έχουν πολλαπλασιασθεί με το 10

            Ακολουθεί άλλο ένα παράδειγμα :

            INTEGER, DIMENSION (5)::A, B, C(15)

            …

            A = (/1, 2, 3, 4, 5/)

            B = (/10, 20, 30, 40, 50/)

            C = (/B, A, B/)

 Οι πίνακες Α και Β θα πάρουν κάποιες αρχικές ακέραιες τιμές, ενώ ο πίνακας C θα πάρει τις 5 τιμές του πίνακα Β, μετά τις 5 τιμές του πίνακα Α και τέλος ξανά τις 5 τιμές του πίνακα Β.

Κι άλλο ένα παράδειγμα :

            INTEGER::C(5)

            REAL::A(10), B(5)

            SUB = (/1, 3, 5, 7, 9/)

            A = (/0.2, 1.2, 2.2, 3.2, 4.2, 5.2, 6.2, 7.2, 8.2, 9.2/)

            B = A(C)

Σύμφωνα με τις παραπάνω εντολές, ο πίνακας Β θα πάρει τιμές από τον πίνακα Α, αλλά μόνο για τις θέσεις 1, 3, 5, 7 και 9, όπως δηλαδή ορίζεται από τις τιμές που περιέχει ο ενδιάμεσος πίνακας C.

Μπορούμε πολύ εύκολα να προσδιορίσουμε τμήματα ενός πίνακα, ως εξής :

            A(2:5, 2)

! δηλώνει το κομμάτι της 2ης στήλης του πίνακα Α που περιέχει

! τα στοιχεία από την 2η έως και την 5η γραμμή

 

A(5, :)

! δηλώνει ολόκληρη την 5η γραμμή του πίνακα Α

 

            A(2:3, 1:4)

! δηλώνει το κομμάτι που ορίζουν η 2η και η 3η γραμμή με την 1η

! και την 4η στήλη του πίνακα Α

 

Η Εντολή ALLOCATE

Με την εντολή ALLOCATE μπορούμε να ορίσουμε δυναμικούς πίνακες στην Fortran 90, δηλ. πίνακες που δεν γνωρίζουμε από την αρχή τις πραγματικές τους διαστάσεις, αλλά μπορούμε να τις δηλώσουμε κατά τη διάρκεια της εκτέλεσης του προγράμματος.

            Ακολουθεί ένα κατατοπιστικό παράδειγμα :

            REAL, DIMENSION(:,:), ALLOCATABLE::A

            …

            READ(5, *) I1, I2

            ALLOCATE (A(I1, I2))

            READ(5, *) ((A(I, J), J=1, I2), I=1, I1)

 

Η Εντολή WHERE

Η εντολή WHERE χρησιμοποιείται για να μπορούμε να επιλέγουμε στοιχεία από πίνακες και έχει ανάλογο αποτέλεσμα με την εντολή IF.

            Ακολουθούν παραδείγματα :

            WHERE (B>0) B = B + 10

            ! μόνο για τα θετικά στοιχεία του πίνακα Β έχουμε αύξηση κατά 10

 

            REAL, DIMENSION(10)::A, B

            READ(*, *) A

            READ(*, *) B

            WHERE(A>0)

                        B=100

            END WHERE

Αφού καταχωρήσουμε όλες τις τιμές στους πίνακες Α και Β, με την εντολή WHERE ελέγχουμε τις θετικές τιμές του πίνακα Α και καταχωρούμε την τιμή 100 στις αντίστοιχες θέσεις του πίνακα Β.

Υπάρχει και η εξής μορφή της εντολής WHERE :

            WHERE(A>0)

                        … εντολές …

            ELSE WHERE

                        … εντολές …

            END WHERE

 

Οι Υπορουτίνες (Subroutines) στη Fortran

Όπως όλες οι γνωστές γλώσσες προγραμματισμού, έτσι και η Fortran, διακρίνει τα υποπρογράμματα (subprograms) σε δύο κατηγορίες, τις υπορουτίνες (subroutines) και τις συναρτήσεις (functions).

Θα δούμε ένα αρχικό παράδειγμα υπορουτίνας που υπολογίζει τον μέσο όρο των αριθμών ενός πίνακα.

            SUBROUTINE MO(N, A, MESOS)

                        DIMENSION A(100)

                        SUM = 0

                        DO I=1, N

                                    SUM = SUM + A(I)

                        END DO

                        MESOS = SUM/N

                        RETURN

            END SUBROUTINE MO

Οι μεταβλητές Ν (πλήθος των στοιχείων για τα οποία θέλουμε να υπολογίσουμε τον μέσο όρο) και Α (όνομα πίνακα) είναι οι παράμετροι εισόδου της υπορουτίνας και η μεταβλητή MESOS είναι η παράμετρος εξόδου της υπορουτίνας. Μόλις συναντηθεί η εντολή RETURN, η υπορουτίνα τελειώνει τη δουλειά της και επιστρέφει τον έλεγχο στο κυρίως πρόγραμμα.

Δεν υπάρχει κάποιος τρόπος για να καταλάβουμε με μια πρώτη ματιά ποιες είναι οι παράμετροι εισόδου και ποιες είναι οι παράμετροι εξόδου μιας υπορουτίνας^ είναι όμως σωστό να γράφουμε μέσα στις παρενθέσεις πρώτα τις παραμέτρους εισόδου και μετά τις παραμέτρους εξόδου.

Το κυρίως πρόγραμμα που καλεί την παραπάνω υπορουτίνα με την εντολή CALL μπορεί να έχει την εξής μορφή :

            DIMENSION A(100)

            READ(*, *) N

            READ(*, *) (A(I), I=1, N)

            CALL MO(N, A, MESOS)

            WRITE(*, *) ‘ΜΕΣΟΣ ΟΡΟΣ = ‘, MESOS

Πρέπει να έχουμε υπόψη μας ότι τα ονόματα των παραμέτρων στην εντολή CALL δεν είναι ανάγκη να είναι τα ίδια μ’ αυτά που υπάρχουν στην υπορουτίνα, αλλά πρέπει οπωσδήποτε να αντιστοιχούν σε πλήθος, σειρά και τύπο δεδομένων.

Μπορούμε με την εντολή RETURN να επιστρέψουμε τον έλεγχο όχι στην εντολή που ακολουθεί αμέσως μετά την εντολή CALL αλλά σε κάποια άλλη εντολή του κυρίως προγράμματος.

            Ακολουθεί ένα παράδειγμα :

            ! ΤΟ ΚΥΡΙΩΣ ΠΡΟΓΡΑΜΜΑ

            …

            CALL SUB1(I, *10, J, *20, *30)

            WRITE(*, *) ‘ΕΔΩ ΕΙΝΑΙ ΤΟ ΚΑΝΟΝΙΚΟ RETURN’

            …

   10     WRITE(*, *) ‘RETURN1’

            …

   20     WRITE(*, *) ‘RETURN2’

            …

   30     WRITE(*, *) ‘RETURN3’

            …

            END

 

            ! Η ΥΠΟΡΟΥΤΙΝΑ

            SUBROUTINE SUB1(I, *, J, *, *)

            …

            IF (I==1) RETURN 1

            IF (I==2) RETURN 2

IF (I > 2) RETURN 3

            …

            RETURN

            END

Στην εντολή CALL χρησιμοποιούμε * για να δηλώσουμε τους αριθμούς των εντολών του κυρίως προγράμματος όπου θα γίνει η επιστροφή από την υπορουτίνα και στις αντίστοιχες θέσεις στην εντολή SUBROUTINE γράφουμε απλά *.

Αν, μέσα στην υπορουτίνα, συναντήσουμε την εντολή RETURN 1, τότε στο κυρίως πρόγραμμα η επιστροφή θα γίνει στον αριθμό εντολής που αντιστοιχεί στο πρώτο * κοκ.

 

Η Εντολή CONTAINS

Χρησιμοποιούμε την εντολή CONTAINS στην περίπτωση που το κυρίως πρόγραμμα και μια υπορουτίνα που καλεί περιέχονται μαζί στο ίδιο αρχείο. Το κυρίως πρόγραμμα μπορεί να περιέχεται σε ξεχωριστό αρχείο από μια υπορουτίνα που καλεί, οπότε θα πρέπει να γίνει ξέχωρα η μεταγλώττιση (compilation) των δύο αρχείων και στη συνέχεια με τη σύνδεση (linking) θα γίνει η ένωσή τους σ’ ένα ενιαίο εκτελέσιμο αρχείο.

Στην περίπτωση λοιπόν που το κυρίως πρόγραμμα και μια υπορουτίνα που καλεί περιέχονται μαζί στο ίδιο αρχείο, θα πρέπει να χρησιμοποιήσουμε την εντολή CONTAINS ως εξής :

            PROGRAM KYRIO

            …

            CALL MO(A, B)

            …

 

            CONTAINS

            SUBROUTINE MO(A, B)

                        …

            RETURN

            END SUBROUTINE MO

            END PROGRAM KYRIO

 

 

Οι Συναρτήσεις (Functions) στη Fortran

Οι συναρτήσεις στη Fortran είναι υποπρογράμματα που μπορούν να δεχθούν μία ή και περισσότερες παραμέτρους εισόδου αλλά επιστρέφουν μία και μόνο μία παράμετρο εξόδου και μάλιστα με το ίδιο όνομα της συνάρτησης.

Η άλλη μεγάλη διαφορά των συναρτήσεων από τις υπορουτίνες είναι ότι οι συναρτήσεις δεν καλούνται με κάποια εντολή CALL αλλά με χρήση του ονόματός τους, όπως ακριβώς καλούνται οι έτοιμες συναρτήσεις των βιβλιοθηκών.

Η σύνταξη μιας συνάρτησης στη Fortran έχει την εξής μορφή :

            [Τύπος] FUNCTION NAME(παρ1, παρ2, …, παρn)

                        [RESULT (NAME1)]

                        … εντολές …

                        RETURN

            END FUNCTION NAME

            όπου έχουμε τα εξής :

Το πρόβλημα της εύρεσης του μέσου όρου των Ν στοιχείων ενός πίνακα Α μπορεί να λυθεί και με τη βοήθεια μιας συνάρτησης ως εξής :

            PROGRAM MAIN

            DIMENSION A(100)

            READ(*, *) N

            READ(*, *) (A(I), I=1, N)

            MESOS_OROS = SUM(N, A)/FLOAT(N)

            WRITE(*, *) ‘ΜΕΣΟΣ ΟΡΟΣ = ‘, MESOS_OROS

            CONTAINS

            FUNCTION SUM(N, A)

                        DIMENSION A(100)

                        SUM = 0.

                        DO I=1, N

                                    SUM = SUM + A(I)

                        END DO

            END FUNCTION SUM

            END PROGRAM MAIN

Ακολουθεί το ίδιο πρόγραμμα αλλά με τη χρήση της εντολής RESULT, όπου ο μέσος όρος υπολογίζεται μέσα στη συνάρτηση και η τιμή επιστρέφεται στο κυρίως πρόγραμμα με το όνομα της μεταβλητής που δηλώνεται στην εντολή RESULT ενώ δεν μπορούμε να χρησιμοποιήσουμε πουθενά μέσα στην ίδια τη συνάρτηση το όνομά της σαν μεταβλητή.

            PROGRAM MAIN

            DIMENSION A(100)

            READ(*, *) N

            READ(*, *) (A(I), I=1, N)

            MESOS_OROS = MO(N, A)

            WRITE(*, *) ‘ΜΕΣΟΣ ΟΡΟΣ = ‘, MESOS_OROS

            CONTAINS

            FUNCTION MO(N, A) RESULT(MESOS)

                        DIMENSION A(100)

                        SUM = 0.

                        DO I=1, N

                                    SUM = SUM + A(I)

                        END DO

                        MESOS = SUM/FLOAT(N)

            END FUNCTION MO

            END PROGRAM MAIN

 

Η Εντολή Συνάρτηση

Η εντολή συνάρτηση (statement function) αποτελεί μια πολύ απλουστευμένη μορφή της συνάρτηση FUNCTION που γνωρίσαμε στην προηγούμενη παράγραφο αλλά που είναι πολύ βολική και χρήσιμη όταν θέλουμε να χρησιμοποιήσουμε έναν απλό τύπο υπολογισμού και δεν θέλουμε να μπούμε στον κόπο να δημιουργήσουμε ένα ολόκληρο υποπρόγραμμα.

Για να δημιουργήσουμε μια εντολή συνάρτηση, γράφουμε το όνομα της εντολής συνάρτηση, μετά μέσα σε παρενθέσεις τις απαιτούμενες παραμέτρους, το σύμβολο = και τέλος τις πράξεις που πρέπει να γίνουν με τις παραμέτρους.

Για παράδειγμα, ας υποθέσουμε ότι θέλουμε να δημιουργήσουμε μια εντολή συνάρτηση που να υπολογίζει το άθροισμα των τετραγώνων δύο αριθμών και να την ενσωματώσουμε σ’ ένα πρόγραμμα. Γράφουμε τα εξής :

            ! ΟΡΙΣΜΟΣ ΤΗΣ ΕΝΤΟΛΗΣ ΣΥΝΑΡΤΗΣΗ

F(A, B) = A**2 + B**2

            READ(*, *) X, Y

            Z = F(X, Y)

            WRITE(*, *) ‘ΑΠΟΤΕΛΕΣΜΑ = ‘, Z

Οι Α και Β αποκαλούνται ψευδομεταβλητές της εντολής συνάρτηση και τα ίδια ονόματα μπορούμε να τα χρησιμοποιήσουμε ξανά μέσα στο πρόγραμμα. Η εντολή συνάρτηση θα πρέπει να γράφεται πριν από την πρώτη εκτελέσιμη εντολή του προγράμματος και δεν μπορεί να χρησιμοποιηθεί σ’ ένα υποπρόγραμμα που καλείται από το κυρίως πρόγραμμα.

 

Η Εντολή COMMON

Με την εντολή COMMON μπορούμε να δώσουμε τη δυνατότητα σε μια ή περισσότερες μεταβλητές να καταλαμβάνουν την ίδια θέση μνήμης.

Η σύνταξή της είναι ως εξής :

            COMMON A1, A2, …, An

            όπου τα A1, A2, …, An είναι ονόματα μεταβλητών.

Για παράδειγμα, αν γράψουμε τις παρακάτω εντολές, στο κυρίως πρόγραμμα την πρώτη και σ’ ένα υποπρόγραμμα τη δεύτερη, στην ουσία θα δημιουργηθούν τέσσερις διαφορετικές θέσεις μνήμης (μεταβλητές) όπου οι Α1 και Β1 θα έχουν ίδια τιμή (ίδια θέση μνήμης), όπως και η Β1 με την Β2 κοκ.

            COMMON A1, A2, A3, A4

            COMMON B1, B2, B3, B4

Αν χρησιμοποιήσουμε την εντολή COMMON σ’ ένα πρόγραμμα, τότε μπορούμε να παραλείψουμε την αναγραφή των μεταβλητών στις εντολές CALL και SUBROUTINE και αυτό γιατί η μεταφορά των τιμών των μεταβλητών γίνεται με την εντολή COMMON.

 Το γνωστό παράδειγμα με τον υπολογισμό του μέσου όρου μπορεί να γραφεί με τη χρήση της εντολής COMMON και ως εξής :

            PROGRAM MAIN

            DIMENSION A(100)

            COMMON N, A, MESOS

            READ(*, *) N

            READ(*, *) (A(I), I=1, N)

            CALL MO

            WRITE(*, *) ‘ΜΕΣΟΣ ΟΡΟΣ = ‘, MESOS

            CONTAINS

SUBROUTINE MO

                        DIMENSION A1(100)

                        COMMON N1, A1, MESOS1

                        SUM = 0

                        DO I=1, N1

                                    SUM = SUM + A1(I)

                        END DO

                        MESOS1 = SUM/N

                        RETURN

            END SUBROUTINE MO

            END PROGRAM MAIN

Στην εντολή COMMON μπορούμε να ορίσουμε τις διαστάσεις και το μέγεθος ενός πίνακα και να μην χρειασθεί να γράψουμε έτσι την εντολή DIMENSION.

            COMMON I, A(100)

 

Η Εντολή INTENT

Με την εντολή INTENT μπορούμε να καθορίσουμε ποιες παράμετροι θα είναι εισόδου σ’ ένα υποπρόγραμμα και ποιες θα είναι εξόδου. Η γενική μορφή της εντολής μπορεί να είναι μια από τις εξής :

            [TYPE,] INTENT (IN)::λίστα_παραμέτρων

            ή

            [TYPE,] INTENT (OUT)::λίστα_παραμέτρων

            ή

            [TYPE,] INTENT (INOUT) ::λίστα_παραμέτρων

Με την πρώτη μορφή της εντολής ορίζουμε ότι οι παράμετροι είναι εισόδου και άρα δεν μπορούν να τροποποιηθούν από το υποπρόγραμμα, με τη δεύτερη μορφή ορίζουμε ότι οι παράμετροι είναι εξόδου και άρα θα πρέπει να λάβουν κάποια τιμή μέσα στο υποπρόγραμμα και με την τρίτη μορφή ορίζουμε ότι οι παράμετροι είναι και εισόδου και εξόδου.

            Ακολουθεί ένα παράδειγμα :

            PROGRAM PROG1

            IMPLICIT NONE

                        INTEGER::A, B, C

                        CALL SUB1(A, B, C)

                        WRITE(*, *) A, B, C

            END PROGRAM PROG1

            SUBROUTINE SUB1(A1, A2, A3)

            IMPLICIT NONE

                        INTEGER, INTENT(IN)::A1, A2

INTEGER, INTENT(OUT)::A3

                        A3 = A1 * A2

            END SUBROUTINE SUB1

 

Οι Εντολές USE και MODULE

Με τις εντολές USE και MODULE μπορούμε να χρησιμοποιήσουμε ένα κομμάτι προγράμματος της Fortran πολλές φορές μέσα στο ίδιο πρόγραμμα αλλά και σε διαφορετικά προγράμματα. Η εντολή USE πρέπει να είναι η πρώτη εντολή στο τμήμα του προγράμματος όπου χρησιμοποιείται.

            Ακολουθεί ένα παράδειγμα :

            MODULE FIRST

                        INTEGER::A1, A2, I

                        REAL::A(100)

            END MODULE FIRST

Αν θέλουμε τώρα να χρησιμοποιήσουμε το παραπάνω κομμάτι προγράμματος σ’ ένα κυρίως πρόγραμμα ή σ’ ένα υποπρόγραμμα, θα πρέπει να γράψουμε πριν από τις εκτελέσιμε εντολές, την εντολή USE ως εξής :

            USE FIRST

Αν θελήσουμε να χρησιμοποιήσουμε μερικά μόνο από τα στοιχεία του MODULE FIRST, γράφουμε το εξής :

            USE FIRST, ONLY::A1, A2

Αν θελήσουμε, μπορούμε να αλλάξουμε το όνομα κάποιας μεταβλητής, ως εξής :

            USE FIRST, ONLY::B1=>A1

 

Έτοιμες Συναρτήσεις Χειρισμού Πινάκων

Η Fortran περιέχει πολλές συναρτήσεις FUNCTION που μπορούμε να χρησιμοποιήσουμε για να κάνουμε πράξεις με πίνακες, που διαφορετικά θα ήμασταν αναγκασμένοι να γράψουμε πολύπλοκο κώδικα. Οι σημαντικότερες από τις συναρτήσεις αυτές είναι οι εξής :

 

Η Παράμετρος KIND

Με την παράμετρο KIND μπορούμε να επιλέξουμε εμείς την ακρίβεια που θέλουμε να έχουν τα δεδομένα μας, έτσι ώστε τα αποτελέσματα να είναι τα ίδια σε διαφορετικά συστήματα υπολογιστών. Στην ουσία επιλέγουμε το πλήθος των bytes που απαιτούνται για την αποθήκευση μιας μεταβλητής.

Η παράμετρος KIND είναι ένας ακέραιος αριθμός που μπορεί να πάρει μια από τις τιμές 4, 8 ή 16 για απλή, διπλή ή και τετραπλή ακρίβεια αντίστοιχα, ενώ σε μερικούς υπολογιστές η ακρίβεια αυτή δηλώνεται με τους αριθμούς 1, 2 και 3 αντίστοιχα.

Αν την χρησιμοποιήσουμε με πραγματικούς αριθμούς, μπορούμε να δηλώσουμε κάποιες πραγματικές μεταβλητές σαν διπλής ακρίβειας ως εξής :

            REAL(KIND=8)::A1, A2, A3

ή

            REAL(8)::A1, A2, A3

Για τις ακέραιες μεταβλητές μπορούμε να χρησιμοποιήσουμε τις τιμές 1, 2 και 4 για ακεραίους με μέγιστες τιμές 127, 32.767 και 2.147.483.647 αντίστοιχα. Η προκαθορισμένη τιμή για τις ακέραιες μεταβλητές είναι η 4.

            INTEGER(KIND=2)::A

            ή

            INTEGER(2)::A

 

Οι Εντολές Τύπου

Υπάρχουν οι έμμεσες εντολές τύπου (implicit type statements) και οι άμεσες εντολές τύπου (explicit type statements). Με τις πρώτες μπορούμε να καθορίσουμε μόνο τον τύπο των δεδομένων των μεταβλητών, των πινάκων και των συναρτήσεων βάσει του αρχικού γράμματος του ονόματός τους, ενώ με τις δεύτερες πρώτες μπορούμε να καθορίσουμε τον τύπο των δεδομένων για ορισμένες μεταβλητές, πίνακες και συναρτήσεις αλλά και τις αρχικές τιμές τους καθώς και τις διαστάσεις των πινάκων.

            Οι έμμεσες εντολές τύπου δηλώνονται με την εντολή IMPLICIT, η γενική μορφή της οποίας είναι η εξής :

            IMPLICIT Type(A1, A2, …), …

όπου έχουμε τα εξής :

Ακολουθούν παραδείγματα :

            IMPLICIT INTEGER(A-D, R-U), REAL(I, L)

Η παραπάνω εντολή δηλώνει ότι όλες οι μεταβλητές που ξεκινούν μ’ ένα από τα γράμματα A έως D και R έως U είναι ακέραιες, ενώ όλες οι μεταβλητές που ξεκινούν μ’ ένα από τα γράμματα I ή L είναι ακέραιες.

            IMPLICIT REAL(I, L), LOGICAL(A-C, Y), COMPLEX(D-F)

            IMPLICIT CHARACTER*10 (A, F)

IMPLICIT CHARACTER*15 FLORINA

Οι παραπάνω εντολές ορίζουν ότι όλες οι μεταβλητές που ξεκινούν μ’ ένα από τα γράμματα A και F είναι αλφαριθμητικές με μήκος χαρακτήρων 10, με εξαίρεση την αλφαριθμητική μεταβλητή FLORINA, η οποία θα έχει μήκος 15 χαρακτήρων.

Οι άμεσες εντολές τύπου είναι πιο περίπλοκες στη σύνταξή τους και θα φανούν καλύτερα με παραδείγματα :

            INTEGER::A, DEIKTIS

Οι μεταβλητές A και DEIKTIS είναι ακέραιες.

            INTEGER A/100/, I

Οι μεταβλητές A και I είναι ακέραιες και η Α έχει αρχική τιμή 100.

            INTEGER A(10), B(5)/1, 3, 3*10/

Οι μεταβλητές Α και Β είναι πίνακες με 10 και 5 στοιχεία αντίστοιχα και ο Β έχει αρχικές τιμές : Β(1)=1, Β(2)=3 και Β(3)=Β(4)=Β(5)=10.

INTEGER A(4)/10, 20, 30, 40/, B(2, 2)/1, 2, 3, 4/

Οι μεταβλητές Α και Β είναι πίνακες, όπου ο Α είναι μονοδιάστατος με 4 στοιχεία και αρχικές τιμές : 10, 20, 30 και 40, ενώ ο Β είναι δισδιάστατος (2 Χ 2) με 4 στοιχεία και αρχικές τιμές : Β(1, 1)=1, Β(2, 1)=2, Β(1, 2)=3 και Β(2, 2)=4. Θα πρέπει να έχουμε υπόψη μας ότι στους δισδιάστατους πίνακες οι τιμές δίνονται κατά στήλες.

            REAL A1/7.2/, A2/3.4/, A3/20.5/

Ορίζουμε τρεις πραγματικές μεταβλητές και δίνουμε αρχικές τιμές.

            COMPLEX A, B(20)

            COMPLEX A1/3, 2/, A2/-4, 15/

 Ορίζουμε μιγαδικές μεταβλητές, όπου στο δεύτερο παράδειγμα έχουμε και απόδοση αρχικών τιμών, δηλ, τις 3+2i και –4+15i.

            LOGICAL D, PASS/.TRUE./, SUCCESS/.FALSE./

            DOUBLE PRECISION A, B(10, 20), C/10.15D2/

            CHARACTER(LEN=10)::NAME

 

Η Εντολή EQUIVALENCE

Με την εντολή EQUIVALENCE μπορούμε να ορίσουμε τις μεταβλητές που θέλουμε να καταλαμβάνουν τις ίδιες ακριβώς θέσεις στη μνήμη του υπολογιστή. Η γενική μορφή της εντολής είναι η εξής :

            EQUIVALENCE (A1, A2, …, An), (B1, B2, …, Bn)

Όπου οι μεταβλητές Α1, Α2, …, Αn καταλαμβάνουν την ίδια ακριβώς θέση στη μνήμη και άρα είναι ισοδύναμες και το ίδιο ισχύει για τις μεταβλητές Β1, Β2, …, Βn, οι οποίες καταλαμβάνουν κάποια άλλη θέση μνήμης.

            Ακολουθούν παραδείγματα :

            EQUIVALENCE (A1, A2, A3)

            A1 = 10

Σύμφωνα με τις παραπάνω εντολές, και οι τρεις μεταβλητές A1, A2, A3 θα έχουν πάρει την τιμή 10.

            DIMENSION A(10), B(10)

            EQUIVALENCE (A(1), B(1))

Οι δύο πίνακες καταλαμβάνουν την ίδια θέση μνήμης, δηλ. ισχύει η αντιστοιχία Α(1)=Β(1), Α(2)=Β(2) κοκ. Αναφέρουμε μόνο τα πρώτα στοιχεία των πινάκων και η ισοδυναμία γίνεται αυτόματα και για τα υπόλοιπα στοιχεία.

 

Η Εντολή DATA

Με την εντολή DATA μπορούμε να αποδώσουμε αρχικές τιμές στις μεταβλητές ενός προγράμματος. Αν στις σταθερές τιμές υπάρχει το σύμβολο *, τότε η σταθερή τιμή που ακολουθεί το * θα επαναλαμβάνεται όσες φορές δηλώνει ο αριθμός που βρίσκεται μπροστά από το *.

            Ακολουθούν παραδείγματα :

            DATA A/10.1/, I/5/, B/13.6/

Η μεταβλητή Α παίρνει την τιμή 10.1, η Ι την τιμή 5 και η Β την τιμή 13.6.

            DATA A, B/15.7, 4.8/

Η μεταβλητή Α παίρνει την τιμή 15.7 και η Β την τιμή 4.8.

            DATA K1, K2, K3/2*10, 20/

Οι μεταβλητές Κ1 και Κ2 παίρνουν την τιμή 10 και η Κ3 την τιμή 20.

            CHARACTER*7, NAME

            DATA NAME/’FLORINA’/

Η αλφαριθμητική μεταβλητή ΝΑΜΕ παίρνει την τιμή ’FLORINA’.

            DIMENSION I(20)

            DATA I/15*5, 5*50/

Τα 15 πρώτα στοιχεία του πίνακα Ι θα πάρουν την τιμή 5 και τα υπόλοιπα 5 στοιχεία την τιμή 50.

CHARACTER*18, A

            DATA A(1:7), A(8:12), A(13:18)/’FLORINA’, ‘ PER ‘, ‘SEMPRE’/

Η αλφαριθμητική μεταβλητή Α παίρνει σταδιακά την τιμή ’FLORINA PER SEMPRE’.

DIMENSION A(10, 10)

            DATA ((A(I, J), J=1, 10), I=1, 10)/100*0./

Ο δισδιάστατος πίνακας Α μηδενίζεται κατά σειρές.

 

Η Εντολή SAVE

Με την εντολή SAVE μπορούμε να αποθηκεύουμε τις τιμές των τοπικών μεταβλητών των υποπρογραμμάτων ανάμεσα στις διαδοχικές κλήσεις τους.

Η σύνταξή της είναι ως εξής :

            SAVE [A1, A2, …, An]

όπου τα Α1, Α2, …, An είναι ονόματα τοπικών μεταβλητών ή πινάκων και αν δεν υπάρχουν καθόλου ονόματα μεταβλητών, τότε αποθηκεύονται οι τιμές όλων των τοπικών μεταβλητών του υποπρογράμματος.

            Ακολουθεί ένα παράδειγμα χρήσης της εντολής :

            PROGRAM MAIN

            …

            DO I=1, 10

                        CALL SUB1(I)

            END DO

END PROGRAM MAIN

 

            SUBROUTINE SUB1(I)

                        SAVE A

                        IF (I==1) THEN

A=1

                        ELSE

                                    A=A+1

                        END IF

                        WRITE(*, *) A

                        RETURN

            END SUBROUTINE SUB1

Θα εκτυπωθούν οι τιμές 1 έως 10 για τη μεταβλητή Α, ενώ αν δεν υπήρχε η εντολή SAVE A, η τιμή της Α θα ήταν 0 κάθε φορά που Ι>1 και έτσι η μεταβλητή Α θα ήταν πάντα ίση με 1, γιατί 0+1=1.

 

back.gif (9867 bytes)

Επιστροφή