Types And Property Resolution
type {}
captures the current context and creates (behaves like?) a nested context.
Accessing a reference inside a type
- check for property on the type
- check for property on any super type
- check for reference in current context (which may include a wrapping type)
Accessing a property on a type
- check for property on the type
- check for property on any super type
add = -> (a<System.Integer>, b<System.Integer>) {
a + b
}
subtract = -> (aa<System.Integer>, bb<System.Integer>) {
aa - bb
}
User = type {
# `name` is an instance property, defined on the type's prototype
@.name = -> { :Thomas }
# `add` resolves to `User.add`, even when called on an instance of `Administrator`
# this is due to lambdas being lexically scoped
# would it be better to force resolution to the module `add` above?
@.age1 = -> { add(12, 13) }
# `@` resolves to the lambda's receiver, which in this case will be an instance of `User` or `Administrator`
# `add` resolves to `User.add`, defined below
@.age2 = -> { @.type.add(12, 13) }
# `subtract` resolves to module-level function above
add = -> (foo<System.Integer>, bar<System.Integer>) {
subtract(22, 12) + foo + bar
}
# `@` is the lambda's receiver, in this case `User`
# `@` will resolve to `Administrator` when referenced below in `Administrator.other`
# `add` resolves to `User.add` or `Administrator.add`, depending on how `create` is accessed
create = -> {
@.add(1, 2)
}
# `self` in a type is a reference to the type
the_type = self
}
# types can inherit from multiple types
# internally ancestors are flattened into a normalized list of ancestors
# all types inherit from `System.Object`, which is always the last ancestor in the list
Administrator = type (User) {
# `name` is an instance property, defined on the type's prototype
@.name = -> { :Allea }
# `subtract` resolves to module-level function above
add = -> (idk<System.Integer>, hero<System.Integer>) {
subtract(42, 2) + User.add(idk, hero)
}
# `@` is the lambda's receiver, in this case `Administrator`
# `create` resolves to `User.create` as `Administrator` inherited from `User`
other = -> { @.create() }
# `Administrator.alias` references the same property as `Administrator.create`, which is inherited from `User`
alias = create
# `the_type` is an inherited reference to `User`
the_sub_type = the_type
# `User` resolves because `Administrator` is defined in the same context as `User`, *not* because `User` is an ancestor
aaaa = User.create()
# call `Administrator.add` defined above
bbbb = add()
# all constructs are available inside a type (or lambda)
cccc = if (aaaa == bbbb) {
'cccc is true'
} else {
'cccc is false'
}
}