We have discussed both kinds of secondary (selections and generators), but there are other points which need mentioning.
There are two kinds of generator (see
section 5.1).
Occasionally, when a procedure has a name parameter, the name may not
be needed. Instead, therefore, of using an identifier of a name which
is used for another purpose, which would be confusing, or declaring a
name just for this purpose, which would be unnecessary, an anonymous
name can be used. For example, a possible call of
the procedure char in string
could be
char in string(ch,LOC INT,str)
if you are only interested in whether the character is in the string and not in its position.
Another case where an anonymous name is useful is in the creation of odd-shaped multiples. Consider the program fragment:
[10]REF[]INT ri; INT j; FOR i TO UPB ri DO read(j); ri[i]:=LOC[j]INT; read(ri[i]) OD
Since there are no declarations in the loop
clause, the scope of the name
created by the generator is the enclosed clause surrounding the loop
clause, which includes the declarations for ri
and
j
. The mode of the slice ri[i]
is REF
REF[]INT
. Thus the value of ri[i]
is a name with
two REF
s in its mode, and it is made to refer to a name
of mode REF[]INT
, which has one REF
less.
Assignments of this type will be considered in detail in the next
chapter. Note that the context of a parameter to read
is
firm so the parameter is dereferenced once before a value is read.
When discussing selections in section 7.2, you may have wondered about the peculiar rules of placing parentheses when talking about rows in structures, rows of structures and rows in rows of structures. Firstly, it should be mentioned that in the secondary
im OF z
where z has mode COMPL
or REF COMPL
, the
z
itself is not only a secondary, it is also a primary
(it is an applied-identifier). This means that
using the declarations
MODE AM = STRUCT(INT i,CHAR c), BM = STRUCT(INT i,AM a); BM b
the selection
c OF a OF b
is valid because
a OF b
is also a secondary. We shall meet extended selections like this in chapter 11.
Secondly, a primary is a secondary, but not necessarily the other way round. Consider these declarations:
STRUCT(INT i,[3]REAL r)s1; [3]STRUCT(INT i,REAL r)s2
The selection r OF s1
has the mode
REF[]REAL
. If you want to slice it, to get one of the
constituent names of mode REF REAL
say, you cannot do so
directly. The reason is that in a slice, as
mentioned in the previous section, what is sliced must be a
primary. To convert the
secondary into a primary you have to enclose it in
parentheses thus converting it into an enclosed
clause; and enclosed clauses are also primaries (in
section 10.1, it was said
that the four classes of units are arranged in a hierarchy in which
each class includes the lower classes). So the second name of r
OF s1
is yielded by (r OF s1)[2]
.
On the other hand, considering the name identified by
s2
, the selection
r OF s2[2]
can be written without parentheses because s2
is not
only a secondary, it is also a primary (an applied-identifier) with
mode REF[]STRUCT...
. The phrase s2[2]
is
perfectly valid, it having mode REF STRUCT(...)
. The
selection r OF s2
has the mode REF[]REAL
and
so it too can be sliced by writing (r OF s2)[2]
. The
effect is the same for both of the cases involving s2
.
Note that the a68toc compiler does not permit
selection of a field from a row of structures. Doing so will yield the
following error message:-
OPERATORS - select: []struct not implemented FATAL ERROR (661) Compiler error: ENVIRONMENT (ASSERT) - assertion failure
To summarise, any primary can be regarded as a secondary, but not vice-versa.
MODE AM = STRUCT(CHAR a,b), BM = STRUCT(AM a, STRUCT(CHAR a,AM b) c, REF BM d); BM pHow many secondaries are there in each of the following units? Ans
a OF p
a OF a OF p
a OF c OF p
a OF a OF d OF p
Sian Mountbatten 2012-01-19