9. Common▲
9-1. L'instruction COMMON▲
L'instruction COMMON
permet le regroupement de zones mémoire pouvant être partagées par différentes unités de programme (fonctions, procédures).
La syntaxe d'une instruction COMMON
est la suivante :
COMMON
[/[nom common
]/] liste variables
Le COMMON
est dit étiqueté si nom_common est précisé. S'il n'a pas de nom, on l'appelle COMMON
blanc.
Les différentes zones regroupées au sein du bloc COMMON
sont adressées via des variables dont les noms sont indiqués dans la partie liste_variables de l'instruction COMMON
. Pour qu'une unité de programme ait accès à ces zones, il est nécessaire qu'elle contienne l'instruction COMMON
les référençant.
9-2. Common blanc▲
Lors de la déclaration d'un COMMON
blanc nom_common est omis et les deux slashes / sont alors optionnels. Ses particularités sont :
- un
COMMON
blanc est permanent (il hérite de l'attributSAVE
) ; -
les variables apparaissant dans un
COMMON
blanc ne peuvent pas être initialisées lors de leur déclaration. Ce type de bloc est initialement constitué de bits à 0. En conséquence :- les données numériques sont initialisées à 0,
- les données logiques sont initialisées à la valeur
.FALSE.
, - les données de type chaîne de caractères représentent des chaînes vides ;
- un
COMMON
blanc peut ne pas avoir la même taille d'une unité de programme à une autre, c'est alors la taille maximum qui sera retenue pour l'ensemble du programme.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
PROGRAM
common_blanc
INTEGER
:: i
INTEGER
, DIMENSION
(6) :: itab
LOGICAL
, DIMENSION
(3) :: ltab
COMMON
itab,ltab
DO
i=1,6
itab(i) = i
END
DO
ltab(1) = .true.
ltab(2) = .false.
ltab(3) = .true.
CALL
sub
END
PROGRAM
common_blanc
!*************************************
SUBROUTINE
sub
INTEGER
:: i
INTEGER
, DIMENSION
(6) :: itab
LOGICAL
, DIMENSION
(3) :: ltab
COMMON
itab,ltab
PRINT
*,'Tableau entier = '
, itab
PRINT
*,'Tableau logique = '
, ltab
END
SUBROUTINE
sub
9-3. Common étiqueté▲
Un COMMON
est dit étiqueté lorsque nom_common est précisé entre caractères /.
Ses particularités sont :
- il peut être initialisé par l'intermédiaire d'une unité de programme de type
BLOCK
DATA
; - un bloc
COMMON
défini dans le programme principal reçoit implicitement l'attributSAVE
. S'il ne l'est pas, l'attributSAVE
est nécessaire si on désire le rendre permanent.
2.
3.
4.
INTEGER
, DIMENSION
(6) :: itab
REAL
, DIMENSION
(12) :: rtab
COMMON
/TAB/itab, rtab
9-3-1. Initialisation : BLOCK DATA▲
BLOCK
DATA
est une unité de programme qui permet d'initialiser des objets déclarés dans des COMMON
s étiquetés :
2.
3.
BLOCK
DATA
[nom_block_data]
[bloc init]
END
BLOCK
DATA
[nom_block_data]
- nom_block_data est le nom du
BLOCK
DATA
; -
bloc_init est une suite :
- de déclarations de type (
INTEGER
,REAL
…), - de déclarations de zones communes (
COMMON
), - d'initialisations statiques (
DATA
).
- de déclarations de type (
Un bloc COMMON
ne peut apparaître que dans un seul BLOCK
DATA
.
On peut se définir plusieurs unités BLOCK
DATA
, chacune regroupant les COMMON
qui ont un lien logique entre eux.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
BLOCK
DATA
INIT
REAL
:: A, B, C, D
REAL
, DIMENSION
(10,15) :: MATRICE
INTEGER
, DIMENSION
(20) :: VECTEUR
COMMON
/BLOC1/ MATRICE, A, B
COMMON
/BLOC2/ VECTEUR, C, D
DATA
A /-1./, B /3.14/, C /0./, D /7.1/
DATA
MATRICE /150 * 50.0/, VECTEUR /20 * 4/
END
BLOCK
DATA
INIT
9-3-2. Instruction SAVE et COMMON▲
Les valeurs des variables d'un COMMON
étiqueté deviennent indéfinies quand une procédure se termine (retour à l'unité appelante) sauf s'il existe une autre unité de programme active le référençant.
Le cas échéant, on lui appliquera l'instruction SAVE
pour conserver son contenu :
SAVE
/nom_common/
- un
COMMON
qui reçoit l'attributSAVE
dans une fonction ou procédure devra toujours être déclaré avec ce même attribut dans toutes les autres unités de programme ; - il est inutile de spécifier l'attribut
SAVE
si leCOMMON
a été déclaré dans le programme principal.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
PROGRAM
common_save
call
first
call
second
END
PROGRAM
common_save
!*************************************
SUBROUTINE
first
REAL
, DIMENSION
(6) :: rtab
LOGICAL
:: drapeau
COMMON
/BLOC/ rtab,drapeau
SAVE
/BLOC/
CALL
random_number(rtab)
PRINT
*,'Afficher le tableau (true/false)'
READ
(*,*) drapeau
END
SUBROUTINE
first
!*************************************
SUBROUTINE
second
REAL
, DIMENSION
(6) :: rtab
LOGICAL
:: drapeau
COMMON
/BLOC/ rtab,drapeau
SAVE
/BLOC/
IF
(drapeau) PRINT
*,'Tableau de réels = '
, rtab
END
SUBROUTINE
second
9-4. Règles et restrictions▲
-
Un
COMMON
ne peut pas contenir :- les noms de procédures (sous-programmes, fonctions),
- les arguments de procédures,
- les constantes symboliques (ayant l'attribut
PARAMETER
) ;
- une même variable ne peut pas apparaître dans 2
COMMON
s de noms différents ; - la taille d'un bloc
COMMON
étiqueté doit être la même dans chaque unité de programme le référençant ; - Fortran 90 permet désormais le mélange de données numériques et caractères au sein d'un bloc
COMMON
; - d'une unité de programme à une autre, les variables de la liste peuvent porter des noms différents ;
- au sein d'une même unité de programme, un bloc
COMMON
(étiqueté ou non) peut être référencé plusieurs fois : les différentes listes de variables sont alors ajoutées les unes aux autres ; - un bloc
COMMON
peut être découpé différemment d'une unité de programme à une autre, c'est-à-dire référencé à l'aide de variables de types différents à condition que ce découpage soit cohérent (les zones numériques doivent correspondre à des zones numériques et de même pour les zones caractères) ; -
une instruction
EQUIVALENCE
ne peut pas :- associer des variables déclarées dans des blocs
COMMON
différents, - avoir pour effet de prolonger le
COMMON
à sa gauche. Dans l'exemple suivant, on ne peut pas associer la variable scalaire A au scalaire B(2) :
- associer des variables déclarées dans des blocs
2.
3.
4.
5.
6.
REAL
:: A
REAL
, DIMENSION
(2) :: B
COMMON
/X/A
EQUIVALENCE
(A,B(2)) ! INVALIDE
EQUIVALENCE
(A,B(1)) ! VALIDE
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
program
common_mixte
complex
, dimension
(10) :: c
character
(len
=100) :: chaine
COMMON
/MIXTE/c, chaine
. . .
call
sub
end
program
common_mixte
subroutine
sub
real
, dimension
(20) :: tab_reels
character
(len
=1), dimension
(100) :: tab_car
COMMON
/MIXTE/tab_reels, tab_car
. . .
! impression des parties réelles
print
*,tab_reels(1:20:2)
print
*,tab_car(1), tab_car(10)
end
subroutine
sub
Recommandations :
- Il est préférable de déclarer un bloc
COMMON
de la même façon dans les différentes unités de programme et donc d'employer la technique de l'exemple précédent avec modération ; - L'instruction
INCLUDE
ci-après favorise le bon emploi des blocsCOMMON
.