![]() | Note |
|---|---|
| Please note that this chapter is incomplete. An update will be published in the future. |
A generic type is a source code template used to define standard types.
Each generic type has a number of parameters which represent types used within the source code template. Each time the type of an object reference (i.e. the type of an attribute, command input/output argument, constant or variable) is specified in the source code template, a parameter can be used as a placeholder, instead of a hardcoded fixed type. Therefore, generic types are also called parameterized types.
A standard type can be defined by using a generic type and specifying a type for each parameter of the generic type. Such a type created from a generic type is called a generified type.
Before explaining the precise rules for defining and using generic types, it might be useful to get a first impression with the following simple example:
generic type pair
param item_type end
type
attribute item1 type: {item_type} end
attribute item2 type: {item_type} end
end
endThe above generic type can be used to define any type that represents a pair of items of the same type. The type of the items is denoted by parameter item_type, and that parameter must be enclosed between { and } whenever it is used in the source code.
A pair of books, for example, can now be defined as follows:
type pair_of_books !pair<book> end
Here is another generified type; a pair of dogs:
type pair_of_dogs !pair<dog> end
Without using a generic type, pair_of_dogs would be coded as follows:
type pair_of_dogs_ attribute item1 type: dog end attribute item2 type: dog end end
![]() | Note |
|---|---|
This is also the code that the compiler creates when generic type |
As we can see so far, generic types are used to define similar types that differ only by their types used for object references.
The syntax for defining a generic type is as follows:
Table 9.1. Generic type syntax
| Production | Syntax | Links |
|---|---|---|
generic_type |
Remarks:
| Chapter 9, Generic types |
generic_type_id | "ge_" ? identifier | |
generic_parameter |
| |
generic_parameter_id | "pa_" ? identifier |
As we can see:
A generic type is introduced with the keywords generic type.
Each generic type is identified by a generic type identifier, which is a prefixed identifier starting with ge_
Each generic type has one or more parameters which are placeholders for types that will be used for object references in the generified types.
Each parameter can be used in the source code of type to specify a variable type for an object reference. The syntax for such a variable type consists of the parameter's identifier enclosed between { and } (e.g. attribute item type: {type_of_item}).
Here is a reprint of the above example of a generic type:
generic type pair
param item_type end
type
attribute item1 type: {item_type} end
attribute item2 type: {item_type} end
end
endThe syntax for defining a generified type is as follows:
Table 9.2. Generified type syntax
| Production | Syntax | Links |
|---|---|---|
generified_type |
| Chapter 9, Generic types |
generic_type_selector | "!" ( library_selector "." ) ? generic_type_id generic_type_parameter_assignments ? | Chapter 9, Generic types |
generic_type_parameter_assignments | "<" generic_type_parameter_assignment ( ";" ? generic_type_parameter_assignment ) * ">" | |
generic_type_parameter_assignment |
( generic_type_parameter_id ":" ) ? object_type_selector
remark: |
As we can see, the body of a generified type is introduced by a !, and then simply defined by referencing the generic type and providing an object type for each parameter in the generic type.
Here is a reprint of the above example of a generified type:
type pair_of_books !pair<book> end
Generified types are used the same way standard types are used.
For example, a variable could be declared as:
var pair_of_books two_books
And, after creating a pair of books, the first book could then be retrieved with:
var book first_book = two_books.item1
A generified type can also be defined 'on the fly'.
'On the fly' means that there is no need to define a type as explained in the previous rule. Instead, the following syntax can be used wherever the type of an object reference (e.g. the type of an attribute) must be specified in source code:
Table 9.3. 'On the fly' generified type syntax
| Production | Syntax | Links |
|---|---|---|
generic_type_selector | "!" ( library_selector "." ) ? generic_type_id generic_type_parameter_assignments ? | Chapter 9, Generic types |
generic_type_parameter_assignments | "<" generic_type_parameter_assignment ( ";" ? generic_type_parameter_assignment ) * ">" | |
generic_type_parameter_assignment |
( generic_type_parameter_id ":" ) ? object_type_selector
remark: |
As we can see the syntax used to define a generified type 'on the fly' is the same as the syntax used in the previous rule.
Thus, instead of declaring a variable as shown in the previous rule:
var pair_of_books two_books
the same can be achieved without defining type pair_of_books, and declaring the variable as follows:
var !pair<book> two_books
Generified types and 'on the fly' generified types can coexist, even if they use the same type parameters. The compiler automatically checks the parameters for generified types, and if two sets of parameters have the same values, then a single common type is used by the compiler.
Currently, two generified types that use the same generic type are considered to be type compatible at compile-time, but a runtime error is immediately raised in case of any type incompatibility occurring at runtime.
![]() | Note |
|---|---|
| This rule will change in a future version, so that type compatibility will be verified at compile-time. |
The following rules define how to define factories that implement generified types. The rules for factories are analogous to those for types.
The syntax for defining a generic factory is as follows:
Table 9.4. Generic factory syntax
| Production | Syntax | Links |
|---|---|---|
generic_factory |
Remark: property 'id' must not be specified for 'factory' | Chapter 9, Generic types |
generic_factory_id | "ge_" ? identifier | |
generic_parameter |
| |
generic_parameter_id | "pa_" ? identifier |
The syntax for defining a generified factory is as follows:
Table 9.5. Generified factory syntax
| Production | Syntax | Links |
|---|---|---|
generified_factory |
| Chapter 9, Generic types |
generic_factory_selector | "!" ( library_selector "." ) ? generic_factory_id generic_type_parameter_assignments ? | Chapter 9, Generic types |
generic_type_parameter_assignments | "<" generic_type_parameter_assignment ( ";" ? generic_type_parameter_assignment ) * ">" | |
generic_type_parameter_assignment |
( generic_type_parameter_id ":" ) ? object_type_selector
remark: |
A generified factory can also be defined 'on the fly' with the following syntax:
Table 9.6. 'On the fly' generified factory syntax
| Production | Syntax | Links |
|---|---|---|
generic_factory_selector | "!" ( library_selector "." ) ? generic_factory_id generic_type_parameter_assignments ? | Chapter 9, Generic types |
generic_type_parameter_assignments | "<" generic_type_parameter_assignment ( ";" ? generic_type_parameter_assignment ) * ">" | |
generic_type_parameter_assignment |
( generic_type_parameter_id ":" ) ? object_type_selector
remark: |