Functionのさわやかさを語らせたら地域一、でおなじみの片山です。
表題のFunctionですが、皆さん意図せずともinvokeしまくっているかと思います。
私もご多分に漏れず呼びまくっていますが、最近引数の数が違うのにFunctionが呼べてしまうという事態に陥りました。
ソースは長いのでこちらにおいておきます。
やっているのは、
に対して、それぞれを引数0個、引数1個(正しい型)、引数2個(第一引数は正しい型)、引数1個(異なる型)を使って呼び出すというテストです。
結果を書くと、こうなります。
引数0個 | 引数1個(正しい型) | 引数2個(第一引数は正しい型) | 引数1個(異なる型) | |
引数0メンバメソッド | ○ | × | × | × |
引数1メンバメソッド | × | ○ | × | × |
引数0ローカルメソッド | ○ | ○ | ○ | ○ |
引数1ローカルメソッド | × | ○ | × | × |
ここで注目すべきなのは、「引数0のローカルメソッドは、どんな引数の場合でも呼び出しに失敗しない」という点です。
従って、例えば「あるFunctionが渡されたときに、そのFunctionが引数ありの場合はコールバックしてもらって、引数なしなら処理続行」という仕様にしたい場合、
public function invoke(f:Function):void{ var callBack:Function = function():void{ //続行処理 }; try{ f(callBack); }catch(e:Error){ //失敗したらコールバックなし f(); callBack(); } }
引数のFunctionがローカルメソッドかメンバメソッドかによって、挙動が変わってしまいます。
public function execute():void{ invoke(member); invoke(function():void{ trace("local"); }); } public function member():void{ trace("member"); } public function invoke(f:Function):void{ var callBack:Function = function():void{ trace("GJ"); }; try{ f(callBack); }catch(e:Error){ trace("invoke fail."); //失敗したらコールバックなし f(); callBack(); } }
これのexecuteを実行すると、
invoke fail. member GJ local
従ってこういう実装をする場合は、引数が少ない順に試していく実装の方が確実な模様です
最近ハマりましたので。。。