I am currently exploring the type system of Swift. Since within a class, a self type can only be used as the result type of methods, I tried out manual encodings using F-bounded type parameters to model classes that are open for covariant refinement. The class Point below abstracts over it's class type via parameter T. T is used in the equalsTo method to only allow comparing Points to Points.
class Point<T: Point<T>> {
let x, y: Int
init(x: Int, y: Int) {
self.x = x
self.y = y
}
func equalsTo(other: T) -> Bool {
return self.x == other.x && self.y == other.y
}
}
The Swift 2 compiler seems to accept the recursively-defined type parameter, but then fails with very strange errors:
line 4: Cannot assign a value of type 'Int' to a value of type 'Int'
line 5: Cannot assign a value of type 'Int' to a value of type 'Int'
line 8: Binary operator '==' cannot be applied to two 'Int' operands
This is clearly a compiler bug, but it's not clear whether, once the compiler is fixed, it will be possible to use F-bounds. Did I overlook any documentation that would explain what can be done with generic types and what isn't possible?
BTW, I tried various alternative encodings. They usually lead to random errors or compiler crashes. For instance, the following code deterministically crashes the Swift 2 compiler:
class Point<T where T: Self> {
...
}
Any help or references to related documentation is very welcome.
Thanks,
Matthias