Vector
import kedr/f32
type Vector3 = struct
x : f32
y : f32
z : f32
Numeric type names are composed of a letter and a size, f32
is a 32-bit floating point number.
Structure can have fields and methods, but not a constructor or destructor. Vector3
contains three fields of type f32
.
let vector = Vector3 1 3 7
vector.z = 8 # fails
vector
is an immutable binding private to a file.
The values 1
, 3
and 7
are positionally assigned to the x
, y
and z
fields.
Single-line comments start with the number sign.
Mutability of a struct propagates to its fields. Binding vector
is immutable, which makes vector.z
immutable as well.
let mut vector = Vector3 1 3 7
vector.z = 8 # works
Binding is made mutable with the mut
keyword.
type Vector3
def norm =
let sum = x * x + y * y + z * z
sum.sqrt
let length = vector.norm
There is no equals sign after the type name, hence it is an extension of the existing Vector3
type.
type Vector3
def norm = x * x + y * y + z * z |> sqrt
Binding sum
can be eliminated using the pipe forward operator. Everything to the left of |>
is computed first, and then sqrt
method is invoked on the result.
type Vector3
def normalize @mut =
let l = norm
x = x / l
y /= l
z /= l
@mut
is an attribute. It forces the method to be called only on the mutable instances of a struct and allows modification of its fields.
type Vector3
def with_x (x : f32) = Vector3 x y z
# fails
The x
parameter shadows the x
field, causing a compilation error.
type Vector3
def with_x self (x : f32) = Vector3 x self.y self.z
# works
Now explicit self
is required to access fields and methods of the type.
type Vector3<T> = struct
x : T
y : T
z : T
We make Vector3
generic by replacing field types with the T
parameter.
type Vector3<T>
def dot (rhs : Vector3<T>) = x * rhs.x + y * rhs.y + z * rhs.z
# fails
Type T
does not support multiplication operator, constraint required.
type Vector3<T> where T : Number
def dot (rhs : Vector3<T>) = x * rhs.x + y * rhs.y + z * rhs.z
# works
Number
is a class with operations common to all numeric types.