神秘的Garbage Collection | (29-10-2004) |
當一個Variable/Object不再需要時,就應該刪除/釋放,以讓出Memory,這種Memory資源管理,稱為Garbage Collection(垃圾回收),簡稱gc。在Flash裡面,熟悉的所謂gc做法有兩種,針對Variable/Object,可以用delete,針對Movie Clip,可以用removeMovieClip()。現實上,delete真的可以刪除垃圾,釋放Memory?當然不是,因為ActionScript裡,凡Array、Object和Function(下面統稱為OBJECTS)的創建,等於建立一個Reference指向Memory某個被佔用位置;因此,當delete OBJECTS時,只不過是刪除這個Reference,斬斷連繫,被佔用Memory仍然存在,根本沒有做到gc。以下是兩個例子: var ref1:Object = new Object(); ref1.name = "Luar"; ref2 = ref1; // 複製新Reference到另一個Variable delete ref1; // 然後刪除ref1 trace(ref1.name); //output: undefined trace(ref2.name); //output: Luar myfunction = function () { 因此,第一次建立OBJECTS,例如ref1、myfunction,是同時做了malloc和建立Reference兩件事,但delete OBJECTS時,只做了刪除Reference,沒有做unmalloc。(註:malloc/unmalloc是C指令,用來分配(佔用)/釋放Memory空間)
trace('Still Here'); }; myOtherfunction = myfunction; delete myfunction; myOtherfunction(); //output: Still Here 根據Flash Help,當一個Memory位置再沒有任何Variable指向Reference它(例如ref1和ref2都delete了),就會自動釋放,換句話說,Flash Player自動替開發者做gc,實在是太好了。原文:You can use the delete operator to remove references to objects. After all references to an object are removed, Flash Player takes care of removing the object and freeing the memory used by that object. 不過,別太早高興,究竟這個自動gc是何時會發生?即時?下一個Frame?沒有人知道。 Movie Clip是Flash獨有的東西,其他編程語言所沒有,由於歷史因素,Movie Clip仍然是用它獨有的建立Object做法:attachMovie()、duplicateMovieClip()和createEmptyMovieClip(),與及獨有的刪除Object做法:removeMovieClip()。(註:unloadMovie()只是將Movie Clip裡東西弄走,沒有刪除Movie Clip) 創建Movie Clip時,可以用一個Variable代表,例如: var myMC = _root.attachMovie("circle", "circle_"+i, i); 避免那用Array Operator("[]")砌出來長長的的Movie Clip名稱,例如:_root["circle_"+i].gotoAndPlay(2); 先用這情況對剛才所講解gc作比喻,Movie Clip好像Memory,myMC好像OBJECTS,刪除了myMC,Movie Clip仍然存在。
提及Movie Clip創建,當然不是只用來作比喻,這裡要提出一個問題,現在用myMC代表了Movie Clip,換句話說,用 myMC.removeMovieClip(); 或_root["circle_"+i].removeMovieClip(); 都可以刪除這個Movie Clip,當直接用Movie Clip名刪除後,myMC是不知道的!它仍然繼續指向undefined,它其實已經沒有用,應該都要刪除。
當然,只要刪除Movie Clip時,同時刪除myMC就可以: _root["circle_"+i].removeMovieClip(); 但這不是好辦法。
delete myMC; 當Movie Clip被刪除時,會發生onUnload事件,利用它,臨死前將myMC一併刪除,但Movie Clip怎知道代表它的Variable是什麼呢?只好在Movie Clip創建時,利用initObject同時告訴Movie Clip,例如: var myMC = _root.attachMovie("circle", "circle", 0, {objName:"myMC"}); 這樣再擴建MovieClip的方法:MovieClip.prototype.onUnload = function() { [下載範例]
delete this._parent[this.objName]; }; 好了,以上的講解,究竟和Design Patterns有什麼關係?因為Movie Clip經常被Composite到其他Object裡,下次繼續。 |
|
本文章由發表。 |
意見 | |
沒有意見。 |
|
同組文章 |