Skip to content

Control flow

if-statement

The conditional execution of logic can be achieved using the if-statement. The consequent is executed only if the boolean expression evaluates to true. Currently, the result of such a statement cannot be assigned or returned.

if (booleanExpr) {
    // consequent
};

If-statements may be nested.

if-else statement or expression

Conditional execution of consequent code when a boolean expression evaluates to true and execution of the alternate for false is to be expressed using if-else. Unlike an if-statement, if-else may serve as an expression and can therefore be assigned or returned.

if (booleanExpr) {
    // consequent
} else {
    // alternate
};

If-else statements or expressions may be nested.

match statement or expression

Match statements or expressions are constructs that are used to branch behavior off a value. Matches may contain any number of cases. When the value matches the case's expression, the corresponding case's code is executed, and the match completes.

Currently, match can only be used in conjunction with Enum and Union.

match (value) {
    caseExpression1 -> {}
    caseExpression2 -> {}
};

An exhaustive match is one where each case is handled, either by explicitly matching all cases in an expression, or through the use of else, which must come last.

match (value) {
    caseExpression1 -> {}
    else  -> {
        // All other cases.
    }
};

Only exhaustive matches may be used as expressions. Non-exhaustive matches may be used as statements, and using a non-exhaustive match statement as an expression is a compile error.

for loop statement

The for loop iterates through items of a collection. Supported types for a collection are List<T> (element is of type T), Set<T> (element is of type T) or a Map<K, V> (element is of type Pair<K, V>). The body of a for loop is a possibly empty block of statements.

The syntax of the for is the following:

for (element in collection) {
    // body
};

For loops may be nested.

Boolean short-circuiting

Boolean expressions in NPL are evaluated left-to-right and short-circuited like in most languages.

This means that for an &&-expression, the right side is not evaluated if the left-hand side evaluates to false. For an ||-expression, the right-side is not evaluated if the left-hand side evaluates to true.

Early return

NPL supports early return out of protocol actions and functions using the return keyword.

function returnEarly(b: Boolean) returns Number -> {
    if (b) {
        return 42;
    };
    return 0;
};

Early return for protocol actions and functions that return Unit is accomplished using return; (omitting the return value).

protocol[p] ReturnEarly() {
    var v: Number = 0;

    permission[p] example(n: Number) {
        if (n > 0) {
            return;
        };

        this.v = v + 1;
    };
}