Structure declarations are very common in Algol 68 programs because they are a convenient way of grouping disparate data elements, but writing out their modes every time a name needs declaring is error-prone. Using the mode declaration, a new mode indicant can be declared to act as an abbreviation. For example, the mode declaration
MODE VEC = STRUCT(REAL x,y,z)
makes VEC
synonymous for the mode specification on the
right-hand side of the equals symbol. Henceforth, new values using
VEC
can be declared in the ordinary way:
VEC vec = (1,2,3); VEC vn := vec; [10]VEC va; PROC(VEC v)VEC pv=CO a routine-denotation CO; STRUCT(VEC v,w,x) tensor
Here is a mode declaration for a structure which contains a reference mode:
MODE RV = STRUCT(CHAR c,REF[]CHAR s)
but we shall consider such advanced modes in chapter 11. Using a mode declaration, you might be tempted to declare a mode such as
MODE CIRCULAR = STRUCT(INT i,CIRCULAR c) CO wrong CO
but this is not allowed. However, there is nothing wrong with such modes as
MODE NODE = STRUCT(STRING s, REF NODE next), PNODE = STRUCT(STRING s, PROC(PNODE)STRING proc)
because the NODE
inside the STRUCT
of its
declaration is hidden by the REF
. Likewise, the
PNODE
parameter for proc
in the declaration
of PNODE
is hidden by the PROC
.
Suppose you want a mode which refers to another mode which hasn't been declared, and the second mode will refer back to the first mode. Both mode declarations cannot be first. In Algol 68 proper, you simply declare both modes in the usual way. However, the a68toc compiler is a single-pass compiler (it reads the source program once only) and so all applied-occurrences must occur later in the source program than the defining-occurrences. In this case, one of the modes is declared using a stub declaration. Here is an example:
MODE MODE2, MODE1 = STRUCT(CHAR c,REF MODE2 rb), MODE2 = STRUCT(INT i,REF MODE1 ra)
There is nothing circular about these declarations. This is another example of mutual recursion. Go ahead and experiment.
This raises the point of which modes are actually permissible. We
shall deal with this in chapter 10. For now, just ensure that you
don't declare modes like CIRCULAR
, and avoid modes which
can be strongly coerced into themselves, such as
MODE WRONG = [1:5]WRONG
If you inadvertently declare a disallowed mode, the compiler will declare that the mode is not legal.
Mode declarations are not confined to structures. For example, the mode STRING is declared in the standard prelude as
MODE STRING = FLEX[1:0]CHAR
and you can write declarations like
MODE FDES = INT, MULTIPLE = [30]REAL, ROUTINE = PROC(INT)INT, MATRIX = [n,n]REAL
Notice that the mode declarations have been abbreviated (by
omitting MODE
each time and using commas). In the
declaration of ROUTINE
, notice that no identifier is
given for the parameter of the procedure. In the last declaration, the
bounds will be determined at the time of the declaration of any value
using the mode MATRIX
. Here, for example, is a small
program using MATRIX
:
PROGRAM tt CONTEXT VOID USE standard BEGIN INT n; MODE MATRIX = [n,n]REAL; WHILE print((newline, "Enter an integer ", "followed by a blank:")); read(n); n > 0 DO MATRIX m; FOR i TO 1 UPB m DO FOR j TO 2 UPB m DO m[i,j]:=random*1000 OD OD; FOR i TO 1 UPB m DO print((m[i,],newline)) OD OD END FINISH
REAL
and one of mode PROC(REAL)REAL
.
AnsVOID
, and the third
being of mode CHAR
.
AnsMODE AMODE = STRUCT(INT i,BMODE b), BMODE = STRUCT(CHAR c,AMODE a)Try writing a program containing these declarations, with names of modes
AMODE
and BMODE
and finish the program with
the unit SKIP
. AnsSian Mountbatten 2012-01-19