Basic support for late binding of Self
This commit adds basic support for late binding of Self types. When a method returns just Self, we now evaluate it into an actual type upon use, instead of upon definiing the return type. The use of Self inside a generic type, such as Array!(Self), still uses early binding.
Supporting simple cases of late binding allows us to clean up
std::range. For example, previously sending successor
to a `Successor
- Compare
would produce a
Successoras the return type. This meant having to cast this back to
Successor + Comparejust to use methods such as
<=. With this commit, the compiler will produce the proper
Successor + Compare` type, removing the need for manually casting anything.
With this commit also come some changes to the return types of bodies of
object, trait, and impl blocks. Previously, the type of these blocks was
set to the object (e.g. Person
in impl Person { ... }
), but this was
not correct. Instead, the block return type should be inferred based on
the last expression returned. These changes don't affect any existing
code, as object/impl/trait themselves return the type of object they
operate on, not what their bodies return.
See #107 (closed) for some more information on binding of Self types.