weakとunownedは対象を所有しませんが、解放後の挙動が違います。weakはnilになり、安全なunownedで解放済みの対象にアクセスすると実行時エラーになります。選択基準は構文ではなく寿命の保証です。
仕組みと設計の判断基準
ARCはコンパイラーが生成する所有権操作と、ランタイムの参照管理が連携する仕組みです。強い循環参照では外部の所有者が消えてもオブジェクトが残ります。unownedもオプショナルにできますが、生存中の対象か明示的なnilに保つ責任があります。 一次資料
再現コード
最初は二つのNodeを互いに所有させ、外部の強参照をなくし、weakで生存を観察して一辺を切ります。次は親から子へ強参照、子から親へweakを使います。最後はOwnerが生存中にunownedオプショナルを手動でnilへ変えます。
この独立したサンプルは2026-10-23に、arm64 macOS向けのApple Swift 6.4をSwift 6言語モードで実行しました。ネットワーク接続や追加パッケージは不要です。
ダウンロード先のフォルダーで実行してください。検証条件を満たさない場合はpreconditionで停止します。検証が削除されるため、-Ouncheckedは使用しないでください。
swift -swift-version 6 swift-arc-weak-unowned.swift
final class Node { var next: Node? }
func breakCycle(_ node: Node) { node.next = nil }
weak var observedA: Node?
weak var observedB: Node?
do {
let a = Node()
let b = Node()
a.next = b
b.next = a
observedA = a
observedB = b
}
precondition(observedA != nil && observedB != nil)
breakCycle(observedA!)
precondition(observedA == nil && observedB == nil)
final class Owner { var child: Child? }
final class Child { weak var owner: Owner? }
weak var observedOwner: Owner?
weak var observedChild: Child?
do {
let owner = Owner()
let child = Child()
owner.child = child
child.owner = owner
observedOwner = owner
observedChild = child
}
precondition(observedOwner == nil && observedChild == nil)
final class Borrower {
unowned var owner: Owner?
init(_ owner: Owner) { self.owner = owner }
}
do {
let owner = Owner()
let borrower = Borrower(owner)
withExtendedLifetime(owner) {
precondition(borrower.owner === owner)
borrower.owner = nil
precondition(borrower.owner == nil)
}
}
print("cycle=retained broken=released weak=nil unowned-optional=manually-cleared")
実行結果と読み取り方
cycle=retained broken=released weak=nil unowned-optional=manually-cleared
強参照の循環はブロック終了後も残りましたが、一辺を切ると両方の観察値がnilになりました。逆向きにweakを使う親子は強参照がなくなると解放されました。unownedオプショナルのnilは自動処理ではなく明示的な代入の結果です。
適用範囲と注意点
このコードは解放済みunownedへのアクセスを実行せず、そのクラッシュを実測したとも主張しません。特定のソース行で必ず解放されるという一般化もできません。最適化や寿命延長が影響します。deinitログがないだけでは、キャッシュなどの正当な所有とリークを区別できません。
次に確認すること
所有グラフを描き、逆方向の関係が所有すべきか判断します。対象の消滅が正常ならweak、アクセス中の生存が保証されるならunownedを検討します。保存したクロージャが所有者を保持する場合はキャプチャの実験へ進みます。
出典と確認基準
- The Swift Programming Language: Automatic Reference CountingSwift.org · 公式ドキュメント · 確認日 2026年10月23日根拠: 実装の契約と説明の根拠です。出力は、この記事に掲載した実験で別途確認しました。

