little self, Big Self
18 Jan 2021 ⇐ Notes archive(This is an entry in my technical notebook. There will likely be typos, mistakes, or wider logical leaps — the intent here is to “let others look over my shoulder while I figure things out.”)
Yesterday I learned — let’s pretend “YIL” is a thing — Swift’s postfix self
(i.e. .self
) can be used after any expression (not just types). It’s a lesser-known arcanum in the language.
1.self // ⇒ evaluates to 1.
"ayy lmao".self // ⇒ evaluates to "ayy lmao".
"ayy lmao".self.count // ⇒ evaluates to 8.
"ayy lmao".self.count.self % 2 // ⇒ evaluates to 0.
Unlike TypeName.self
metatype expressions, SomeExpression.self
postfix self expressions evaluate to the value of the expression. Which adds color to the decision behind \.self
as the identity key path — it’s a sort of postfix self as a key path. QuinceyMorris noted in a Swift Forum’s thread that this precedent comes from the Objective-C days,
For historical, Objective-C* reasons, you can add
.self
to pretty much any expression and the resulting value is that same expression’s value.[…]
*In Objective-C, [key-value coding (KVC)] always requires an object and a non-empty key-path to access a value. To reference the object itself, you don’t have a key-path, so
NSObject
defined aself
method, which works as key-path “self” in KVC. It works like this in Swift, too:
let myself = self[keyPath: \.self]
⬦
To make things doubly esoteric, I might’ve had too much cold brew one morning when I realized Self.self
is a valid expression and can be used to back Identifiable
conformances for one-off alerts or sheets in SwiftUI.
Self.self
allows id
to follow suit with the type’s name, if it’s ever refactored down the line.
⬦
For more on Swift’s other self
s, Jesse Squires has you covered in a recent blog post.