Skip to main content
Version: 7.0

Expression

An expression is a combination of property operators and parameters. When an expression is evaluated sequentially in priority order, all the operators are executed.

The result of that execution will be either a property or a parameter (in the case of single-parameter expression). Their value shall be called the value of the expression.

An expression can be described by the following set of recursive rules:

RuleDescription
expression := parameter | constant | prefixOperatorA single parameter, constant, or non-arithmetic prefix operator
expression := prefixArithmOp expressionA unary arithmetic prefix operator, with the expression passed to it as an operand
expression := expression postfixOpA unary postfix operator, with the expression passed to it as an operand
expression := expression binaryOp expressionA binary operator with the expressions passed to it as operands
expression := ( expression )Expression in parentheses

When the syntax of an operator ends with a comma-separated list of expressions without enclosing parentheses (as in OVERRIDE expr1, expr2), the list extends to the end of the expression the operator is part of: the operators to the right belong to its last element, and a comma after it adds one more element rather than ending an enclosing list such as the arguments of a property call. When an operator to the right must apply to the result of such an operator, or another argument must follow it in an enclosing call, the operator together with its operands is enclosed in parentheses: (OVERRIDE a, b) + 1, f((OVERRIDE a, b), c).

An expression cannot include context-independent property operators.

Using actions inside expressions​

Inside an action body, an expression can also use a call to an action that returns a result, treating it as a property. In this case the parentheses first list the values of the action's input parameters, and then the new local parameters that become the names of the result's parameters for further use in the expression.

Such a call is equivalent to the sequential execution of:

  • creation of a local property with the signature of the action's result;
  • call of the action with the result written into that local property;
  • substitution of that local property into the expression.

Action calls in expressions are only allowed inside an action body.

Examples​

CLASS Team;

wins(team) = DATA INTEGER(Team);
ties(team) = DATA INTEGER(Team);

// The number of points received by the team for the matches played
points(Team team) = wins(team) * 3 + ties(team);
// In this case, the expression is written to the right of the equal sign. It defines a new property called points.
// When calculating the expression, two JOIN operators are first executed: wins(team) and ties(team), substituting
// the team parameter in the wins and ties properties. Then the multiplication operator will be executed,
// which will build a property that returns a number equal to the product of the return value of wins(team)
// and the number 3. Then the addition operator will be executed, which will create a property that sums the return
// values (wins(team) * 3) and ties(team). The resulting property will be the result of the expression.

CLASS Game;
CLASS BonusGame : Game;

// The number of points per game. If the game is bonus, then 3, otherwise 2.
gamePoints(Game game) = 2 (+) (1 IF game IS BonusGame);
// In this example, the order of execution of the operators will be as follows: IS, IF, (+)

CLASS Item;
price(Item i) = DATA INTEGER (Item);
label(Item i) = DATA STRING[100] (Item);

priceBucket (INTEGER p) {
IF p > 1000 THEN RETURN 'high';
IF p > 100 THEN RETURN 'mid';
RETURN 'low';
}

// call of action priceBucket inside an expression in the body of another action
labelItem (Item i) {
label(i) <- 'Bucket: ' + priceBucket(price(i));
}