Arithmetic Expression

The type of an arithmetic operator is the type of the expression that contains it. Operands are automatically coerced to the type of the operator.

In this example the variables are named for their type. The type of the the assignment variable (a cell) determines the type of expression operations on the right hand side. The Byte and Double values are implicitly coerced to a Cell. In this case the Byte value is sign extended to a Cell.

   Cell = Byte * (Cell + Double)

In languages in which operators derive their type from their operands, a set of rules is needed to determine what to do when operand types do not match. In Gilda there is no ambiguity and no such rules are required. As you read an expression it is easy to figure out type coercions. In practice it also turns out that fewer explicit type casts are needed.

Expressions may be nested within matched pairs of parenthesis; which can be "()", "[]" or "{}" characters; your choice. The only String operator is concatenation for which an exclamation point ("!") is used. Real arithmetic operations are always signed.

       Operator                 Description                          Precedence

                 ~  E      Signed unary complement                       1
     +  E        -  E      Signed unary plus and minus                   1
               E ^  E      Signed real, unsigned integer exponentiation  2
   E *  E      E /  E      Signed Multiplication and division            3
               E %  E      Unsigned integer or IEEE real remainder       3
   E _* E      E _/ E      Unsigned multiplication and division          3
   E \\ E      E // E      Logical shift left and right                  3
   E << E      E >> E      Circular shift left and right                 3
   E +  E      E -  E      Signed addition and subtraction               4
               E /\ E      Logical And                                   5
   E \/ E      E -- E      Logical Or and Exclusive Or                   6

Since integer variables can be treated as either signed or unsigned, operators for unsigned multiplication and division are provided:

     _*    _/

Overall this is easier to work with than having signed and unsigned integer type declarations. You can tell if an operation is unsigned without referencing the type declaration.

The exponentiation operator (^) is unsigned for integer arguments and signed for floating point arguments. Note that a signed real base may not have a fractional exponent. In this case the result is complex and a fault exception is raised. Unsigned integer exponentiation is computed in log2 time using the following algorithm:

    Power = if Exponent /\ 1, Base, 1;  Initial value.

    IF Exponent // 1:                   IF Exponent is 2 or more,
       DO always:                          DO over each bit in the Exponent,
          Exponent //= 1;                     Shift out the low bit.
          Base     _*= Base;                  Square the base.

          IF Exponent /\ 1:                   IF the low bit is set,
             Power _*= Base;                     Scale Power by the Base.
       UNDO IF Exponent = 1;               UNDO IF no more Exponent bits.
    .  -  .

Arithmetic expressions and conditions are pure in that they have no side effects. They only read memory and can not perform I/O operations or raise managed exceptions. Like anything else they can raise faults such as division by zero. This distinction is discussed further in the section on Exceptions.

Array Variable

Conditional Expression