下書きはいっぱいあるけど初投稿なsu10です。
AS3で強制的に引き起こすことができるガベージコレクション(GC)について調べたのでまとめます。
最後に紹介する強制GCは他では見たことないはず・・・。
System.gc()
flash.system.System.gc()
を使うことでGCを強制することができます。
Adobeの公式リファレンスによると、
言語バージョン: ActionScript 3.0
ランタイムバージョン: AIR 1.0, Flash Player 9.0.115.0, Flash Lite 4
ガベージコレクションプロセスを強制します。
Flash Player デバッグ版および AIR アプリケーションのみ。AIR アプリケーションでは、System.gc() メソッドは AIR Debug Launcher(ADL)で実行しているコンテンツ、またはインストールされているアプリケーションではアプリケーションセキュリティサンドボックスのコンテンツでのみ有効になります。
というわけで、基本的にはデバッグ用途で開発時に利用するもののようです。
LocalConnection#connect()を2回呼出す
黒魔術っぽいのですが、LocalConnection#connect()
を2回呼出すことでGCを強制できます。
こちらで紹介されてるので詳細はリンク先を見てもらうとして、GCを起こすのに必要なコードだけ載せると以下のようになります。
try {
new LocalConnection().connect("test");
new LocalConnection().connect("test");
} catch (errorObject:Error) {}
これを適当にgc()
とか名前をつけたメソッドにまとめてGCを起こしたいタイミングで呼び出せばOK。
ただ、
初めに述べたように正規サポートの機能ではありませんので、テストや実験などの範囲で使うのがよいでしょう。
とのことで、やはり本番では使わないほうがよさそうです。
Loader#unloadAndStop()を使う
リファレンスをなんとなく読んでて以下を見つけました。
言語バージョン: ActionScript 3.0
ランタイムバージョン: Flash Player 10, AIR 1.5, Flash Lite 4
子 SWF ファイルの内容のアンロードを試み、ロードされた SWF ファイルのコマンドの実行を中止します。
(中略)
注意(iOS のみ):AIR 3.6 より前のバージョンでは、iOS ではこのメソッドの効果はありません。
パラメーター
gc:Boolean (default = true) — 子 SWF オブジェクトでガベージコレクターが実行されるようにヒントを提供するかどうかを指定します(true または false)。多数のオブジェクトを非同期でアンロードする場合は、gc パラメーターを false に設定するとアプリケーションのパフォーマンスが向上する可能性があります。ただし、このパラメーターを false に設定した場合は、unloadAndStop() コマンドの実行後も子 SWF ファイルのメディアオブジェクトおよび表示オブジェクトがメモリに残ることがあります。
unloadAndStop()
でGCが起きるようです!
ということで試してみました。
Loader#unloadAndStopで強制的にGCを起こせるかどうかテスト - wonderfl build flash online
Loader#unloadAndStopで強制的にGCを起こせるかどうかテスト2 - wonderfl build flash online
あんまり自信がなかったので2パターン試しました。
コア部分のコードは以下のようになります。
var loader:Loader = new Loader();
var byteArray:ByteArray = (new JPGEncoder()).encode(new BitmapData(1,1));
// NOTE: 何かしらロードしてないとunloadAndStopでGCが走らない
loader.loadBytes(byteArray);
// GCを強制的に引き起こす
loader.unloadAndStop();
コメントで軽く書いてますが、何もload()
とかloadBytes()
してない状態でunloadAndStop()
を呼んでもGCが走らないようなので適当に小さいByteArrayをloadBytes()
してからunloadAndStop()
を呼び出してます。
リファレンスに載ってる挙動だし本番でも使えそう!
余談
GCを抑えたいときは結構あると思うんですが、強制したいときってあるんでしょうか?・・・