16.1 Structs
You can also have named structures as in C:
struct X { a:int; b:double; }; var x:X = X(1,2.2); println$ str x.a + str x.b;
Each struct
has an autogenerated constructor which takes a tuple
of values of types in the same order as declared in the struct
definition.
Whilst struct
s are similar to records, records are structurally typed,
or anonymously typed. This means you can just create a value
of a record type, without declaring the type.
For a struct
however, you must first declare the type and give it a name:
they're said to be nominally typed. This means two struct
s with the
same components but declared with distinct names are distinct types.
16.1.1 Accessor Methods
You can also define fun
ctions in a struct
like this:
struct complx { x: double; y: double; fun arg => tan (self.x/self.y); fun mod => sqrt (self.x * self.x + self.y * self.y); fun add (z:complx) => complx(self.x + z.x, self.y + z.y); } var z = complx(0.5, 0.5); println$ z.x, z.y, z.arg, z.mod; var a = z.add z; println$ a.x, a.y;
Accessor functions are ordinary function which just get an extra
argument called self
of the type of the struct
.
16.1.2 Mutator Methods
You can also define mutators in a struct
.
struct complx2 { x: double; y: double; proc doset (xx:double, yy:double) { self.x <- xx; self.y <- yy; } } var b = complx2(1.0,2.0); (&b).doset (0.7, 0.8); println$ b.x, b.y;
Note that mutators require a pointer argument.
To make it easier, to work with fields and pointers Felix provides two special syntax sugars:
Sugar Meaning ------- ---------- p*.mem (*p).mem v&.mem (&v).mem v = x; (&v) <- x;