既に周知のことではありますが、JSとASの
両方を書いたりしていると、うっかりミス
をすることもあるので、備忘録的にメモ..
JavaScriptの場合、thisは実行時のコンテキスト
オブジェクトになります。
一方、ActionScript3はJavaに近くなっており
var objA = {
name: 'John',
dispName: function() {
alert(this.name);
}
};var objB = {
name: 'Betty'
};objB.dispName = objA.dispName;
objA.dispName(); //結果は「John」
objB.dispName(); //結果は「Betty」
thisはあくまで元のインスタンスを指します。
public class ClassA {
public var name:String = "John";
public function dispName():String {
return this.name;
}
}
public class ClassB {
public var name:String = "Betty";
public var dispName:Function;
}
ところが、クラスのメソッド定義ではなく
import flash.display.*;
import flash.text.*;public class Main extends Sprite{
public function Main(){
var tfA:TextField = new TextField();
var tfB:TextField = new TextField();var a:ClassA = new ClassA();
var b:ClassB = new ClassB();b.dispName = a.dispName;
tfA.text = a.dispName();
tfA.y = 10;tfB.text = b.dispName();
tfB.y = 40;addChild(tfA); //結果は「John」
addChild(tfB); //結果は「John」
}
}
関数型プロパティに無名関数を設定した形
で記述すると、JavaScriptの場合と同様に
なります。
public class ClassC {
public var name:String = "Kathy";
public var dispName:Function = function():String{
return this.name;
}
}
public class ClassD {
public var name:String = "Robert";
public var dispName:Function;
}
メソッドの場合はインスタンスにバインドされるけれども
import flash.display.*;
import flash.text.*;public class Main extends Sprite{
public function Main(){var tfC:TextField = new TextField();
var tfD:TextField = new TextField();var c:ClassC = new ClassC();
var d:ClassD = new ClassD();d.dispName = c.dispName;
tfC.text = c.dispName();
tfC.y = 10;tfD.text = d.dispName();
tfD.y = 40;addChild(tfC); //結果は「Kathy」
addChild(tfD); //結果は「Robert」
}
}
関数プロパティとした場合には無名関数がインスタンスと
独立して存在しているということですね。確かにコードを
見るとそういう動きが妥当な感じがします。
しかしながら、無名関数の場合でもthisを省略すると
インスタンスにバインドされた状態になります。
public class ClassE {
public var name:String = "Mike";
public var dispName:Function = function():String{
return name;
}
}
public class ClassF {
public var name:String = "Beth";
public var dispName:Function;
}
上記の場合はコードをパッと見てもバインド
import flash.display.*;
import flash.text.*;public class Main extends Sprite{
public function Main(){var tfE:TextField = new TextField();
var tfF:TextField = new TextField();var e:ClassE = new ClassE();
var f:ClassF = new ClassF();f.dispName = e.dispName;
tfE.text = e.dispName();
tfE.y = 10;tfF.text = f.dispName();
tfF.y = 40;addChild(tfE); //結果は「Mike」
addChild(tfF); //結果は「Mike」
}
}
されているというのを見落としてしまいがち
かも知れません。
thisは省略せず、処理内容を動的にしたい場合は
関数型プロパティに代入、静的で構わない場合は
メソッドで定義というのが無難なスタンスかなと
いう気がします。
こういう微妙な動作の違いも面白いですね。