Last active
November 4, 2018 07:01
-
-
Save creaaa/1001bdf293cd8444a42f85ca66d3761b to your computer and use it in GitHub Desktop.
staticなプロパティの生存期間
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import UIKit | |
class StaticClass { | |
static var pokemon = Pokemon(name: "Pikachu") | |
deinit { | |
print("static class died") | |
} | |
} | |
class Pokemon { | |
let name: String | |
init(name: String) { | |
print("\(name) was born") | |
self.name = name | |
} | |
deinit { | |
print("\(name) died") | |
} | |
} | |
class ViewController: UIViewController { | |
override func viewDidLoad() { | |
super.viewDidLoad() | |
let pikachu1 = StaticClass.pokemon | |
let pikachu2 = StaticClass.pokemon | |
print(pikachu1 === pikachu2) // true | |
StaticClass.pokemon = Pokemon(name: "リザードン") // Pikachu died | |
} | |
} | |
// 1. タイププロパティの値の式は、アクセスされた時点で初めて評価される(lazyと似ている) | |
// 2. タイププロパティの値を格納した変数が死んでも、タイププロパティの値(Pickachuインスタンス)は生存し続ける。 | |
// (∵ カウント0かと思いきや、 | |
// プロパティ StaticClass.pokemon には参照され続けており、ARCカウント+1になっているので) | |
// このタイププロパティ StaticClass.pokemon 自体をアプリから亡き者にするのは超AAA級、相当難しいだろう... | |
// ただ、StacicClass.pokemon に別のポケモン(リザードン)を代入すると、 | |
// Pikachuインスタンスのdeinitが呼ばれる("Pikachu died と表示される) | |
// ∵ Pokeomon(Pikachu)を指している変数はいまやなくなったから |
プロパティがstaticになった時点で、(private出ない限り)どこからでもアクセスされてしまう。
アクセスを、"ある機能を司る画面内からのみに制限する"のは、相当難しそうだな...
本気なら、staticではなく、別の手段を考えたほうがよさそう
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
結論
タイププロパティ変数に代入されているインスタンスを殺す方法は、var であれば、再代入することで参照カウントを0にすること。
そのタイププロパティがlet だったり、privateだったら99.999%無理だろう。
また、タイププロパティ自体を殺すのは相当難しいだろう。ほぼ不可能と言って良い。
タイププロパティとは「型」に紐づくもの。
インスタンスには生死が問題になるが、タイプ(型)はインスタンスを生み出すための設計図であり、
インスタンスとして生まれることもなければ死ぬこともなく、アプリ起動中、「ただ、そこにあるもの」。
そんな「タイプ」のプロパティ(プロパティに代入されている値ではない)を、果たしてどうやって殺せというのか。