What happens if I smuggle self
out of my deinit
, by assigning it to some external strong reference? This code below is clearly not well formed:
class C: CustomStringConvertible {
let s = "abc"
var description: String {
return "C(id: \(ObjectIdentifier(self)), s: \(s))"
}
deinit {
print("deinit")
globalObject = self
}
}
var globalObject: C!
do {
let localObject = C()
print("localObject: \(localObject)")
print("end of `do`")
}
print("globalObject: \(globalObject!)")
You can't just "change your mind" about the deinitialization of an object, from the middle of a deinit
. But interestingly, this code is non-deterministic, and it does occasionally sometimes complete successfully, printing:
localObject: C(id: ObjectIdentifier(0x00007f9063f00960), s: abc)
end of `do`
deinit
globalObject: C(id: ObjectIdentifier(0x00007f9063f00960), s: abc)
I'm running this using Code Runner, which is just running a single file Swift script using swiftc
. So there's no unexpected Playground-owned references at play here.
Where's the non-determinism coming from?
swiftc --version
givesApple Swift version 5.1 (swiftlang-1100.0.212.5 clang-1100.0.28.2) Target: x86_64-apple-darwin19.0.0
– Wriest