Swift Incomplete Feature: Closed Constructed Types

I’ve been encountering limitations with Swift’s generics, some of which C# doesn’t have, regarding closed constructed types. Here are a couple, to start off with. I’ll update with more examples of potential use cases as I think of them.

Vector Math

If you don’t work with vector math, you should probably just skip this section.

If you’re still reading, I’ll assume you know why this is handy:

struct Vector4<T> {
    init(_ x: T, _ y: T, _ z: T, _ w: T) {components = [x, y, z, w]}
    let components: [T]
}

Sometimes, it’s useful to have the w component represent a common default: typically 1, but often 255, for colors. We can’t use a default value in that initializer, because we don’t know the type of T. But it seemed easy enough, to me, to pump that data into closed constructed types:

extension Vector4<FloatLiteralConvertible> {
    init(_ x: T, _ y: T, _ z: T) {self.init(x, y, z, 1.0)}
}

extension Vector4<UInt8> {
    init(_ x: T, _ y: T, _ z: T) {self.init(x, y, z, UInt8.max)}
}

ERROR! Generic arguments are not allowed on an extension.

Mr. Pump

Mr. Pump, I’m afraid our homogenous coordinates will require some serious overtime.

 

Inheritance

I recently logged two (fortunately both duplicate) bugs about not being able to use generic classes as delegates in UIKit, which is due to them not working with Objective-C. In my case, knowing that TextFieldDelegate<Int> wouldn’t work, I went the route that I’m used to going, when circumventing not being able to serialize generics in Unity:

class TextFieldDelegate_Int: TextFieldDelegate<Int> {}

ERROR! Classes derived from generic classes must also be generic.

TextFieldDelegate<Int> is not a generic class. It is a closed constructed type.

Leave a Reply

Your email address will not be published. Required fields are marked *