ActionScript3 Function研究

來源:http://www.kingda.org/archives/kingda/2006/06/actionscriptfunction1.html

Function究竟是什麼?
我們習慣了function的存在,就像習慣了我們呼吸的空氣卻不去探究它的本質。看起來,似乎function和Number, Boolean, String一樣都是ActionScript本來就有的類型

先看以下代碼:


trace (aFunc); //輸出:[type Function]
trace (aFunc instanceof Function); //輸出:true
trace (aFunc instanceof Object); //輸出:true

function aFunc() {
trace (“This is aFunc!Excuted!”);
}


第一行告訴我們aFunc的類型是Function, 第二行又證實了這一點aFunc確實是一個Function類型的實例,第三行更加有意思告訴我們aFunc是一個Object。
初學者可能很驚奇,其實AS2.0中除了原始數據類型Number, Boolean, String,undefined, null,其餘全是Object. 而AS3.0中則更加極端,一切皆對象。包括原始數據類型也是Object,只不過是特殊的不變對象(immutable objects)類型。與主題扯遠了,打住。laughing.gif

Function本質上到底是怎樣的一種Object?
與其他編程語言不同,在AS中, Function是一個Object,可以有獨立的屬性甚至方法。比如arguments,callee,caller。在AS3.0 中,Function還由更多的屬性。
函數一旦執行,一個特殊的對象就建立了。我們稱它爲"active object",它含有以上的屬性和本地變量。這個對象我們是不可訪問的,屬於內建的機制。同時,每個Function都含有一個內置的範圍鏈 (scope chain),這時也將被建立,以使Flash Player來檢查所有的聲明。函數可以層層嵌套,範圍鏈也是如此。最大的範圍鏈那當然是Global函數的範圍鏈了,包括所有的全局變量和函數。


知道了Function 是Object又怎樣?
會給我們帶來極大的便利和編程思維的改變:
運用一:這是簡單運用, 設立一個代理函數對象,根據條件的不同,將它指向不同的函數,實現動態改變。相信有經驗的程序員都瞭解動態改變函數的便利性。而且由於AS提供了這種便 利,運用這個特性可以衍生大量技巧。


var kingdaFunc:Function;
var sex:String = "male";
if ( sex == "male") {
kingdaFunc = maleFunc;
} else {
kingdaFunc = femailFunc;
}
kingdaFunc(); //輸出: I am a boy

function maleFunc() {
trace ("I am a boy");
}
function femaleFunc() {
trace ("I am a girl");
}

運用二:建立函數執行隊列。
比如說,我有一個對象,我想根據不同的情況對它進行一系列的操作。但是有時需要所有的操作,有時又只需要一部分的操作。那麼這個較高級的技巧,就能保證代 碼的高度重用性和簡潔。


var funcAry:Array = new Array();

//將需要的操作步驟加入隊列
funcAry.push(aFunc);
funcAry.push(bFunc);
funcAry.push(cFunc);

//供操作的對象
var originObject:Object = new Object();

//需要執行幾步由execQueue這個參數決定,在實際工程運用中這個數可能是動態決定的。
var execQueue:Number = funcAry.length;

/核心步驟:/函數隊列執行。實際運用中可以把它包裝成一個函數,或者一個類的實例。
for (var i:Number =0; i
funcAry[i](originObject);
}

//trace出執行操作後的originObject裏面的內容
for (var i in originObject) {
trace ( i + ":" + originObject[i]);
}

//操作步驟a,b,c
function aFunc(eO:Object) {
eO.aFuncExected = true;
trace ("aFunc()");
}
function bFunc(eO:Object) {
eO.bFuncExected = true;
trace ("bFunc()");
}
function cFunc(eO:Object) {
eO.cFuncExected = true;
trace ("cFunc()");
}


輸出內容爲:

aFunc()
bFunc()
cFunc()
cFuncExected:true
bFuncExected:true
aFuncExected:true

前三行表明a,b,c三個函數按順序執行了。後三行表明orginObject確實經過了三步操作,多了三個爲true的屬性。

黑羽提醒:技巧可以再延深!
可以通過一個函數來管理隊列裏面各個元素的位置,達到改變操作函數的順序。比如通過一個數組來安排調用順序


var operationAry:Array = [2,1,0]
for(var i:Number = 0; i
funcAry[operationAry[i]](originObject);
}

這樣函數就通過2,1,0這樣的倒序來執行操作。

這個技巧還有很多可以延伸的地方,比如說動態控制操作函數的參數等等,供大家自己研究擴展。

發佈了54 篇原創文章 · 獲贊 7 · 訪問量 16萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章