99 Program Variables as Locations


var status = 0;
status := 25;

var Integer id* = {};
id := s.supplier.id;

The declaration var status = 0; creates a mutable program location named status. Its element type is Integer, its cardinality is one, and status := 25; replaces the contents of that location with the single value 25.

The declaration var Integer id* = {}; creates a mutable program location whose element type is Integer and whose cardinality is zero or more. The expression s.supplier.id may reach many values, so assigning it to id is valid only because the target location permits many values.

This is the same unary-predicate reading used for attributes. The name id is singular because it names one predicate location. The * constrains the extension of that location; it does not change the element type to a set type. Thus var Integer id* = {}; should be read as “the id extension contains zero or more Integer values,” not as “id is a Set<Integer> value.”


var id1 = 0;
id1 := s.supplier.id;     // static cardinality constraint check failure

var Integer id2* = {};
id2 := s.supplier.id;     // ok

The first assignment is rejected statically. The declaration var id1 = 0; gives id1 cardinality one, while the path s.supplier.id has a static cardinality that may be many. This is a static cardinality constraint check failure, not a static type check failure: both sides have element type Integer. No query is executed to discover this error.

A program variable has two denotations. In an expression context, the variable denotes the value or extension obtained by reading its location. In an update target context, the same variable denotes the location itself. The assignment operator writes a replacement extension to that location after checking the element type and cardinality constraint.


var B b* = { A { x = 1 }, A { x = 2 } };

The cardinality qualifier belongs to the variable location, not to the element type. In var B b* = ...;, each member assigned to b must have element type B; the * says the location may contain zero or more such members. The variable's element type is still just B.

The keyword var still introduces a statically typed variable. The element type may be inferred from the initializer, as in var status = 0;, or supplied explicitly, as in var Integer id* = {};. An empty initializer does not by itself determine an element type, so an explicit type annotation is required unless another expected type is available from the surrounding context.

A typed variable may be declared without an initializer:


var String message;

Such a variable is uninitialised. A declaration with neither an explicit type nor an initializer, such as var message;, is a static error because its type cannot be inferred. The legality of declarations, reads, and partial initialisation is specified in Uninitialised Locations.

Updating a program variable is a local program-state update. It does not require a database transaction and is not committed or rolled back by the database transaction mechanism.