2011-01-09 13 views
3

fを指すメソッドの名前を取得するには、関数fが必要なことがよくあります。例えば。我々はmethodFunctionへのリンクであるプロパティを見つけるためにobjforeachを使用していますgetMethodName(obj, methodFunction)機能を持っているとしましょう:厳密モードのJavaScriptで "self"関数を取得する

obj = { 
    foo : function() { 
     var myName = getMethodName(obj, arguments.callee); // "foo" 
    } 
} 

私はarguments.calleeが廃止されましたstrictモードでこれをどのように行うのですか?

答えて

4

あなたはできません。最初はやってはいけません。これは魔法です。あなたの関数は呼び出し元に依存してはいけません。再び動作させるために、デザインを変更してください。

arguments.calleeおよび.callerは、スタイルが悪いだけでなく、最適化を無効にするために削除されているだけでなく、つまり、インライン展開では、呼び出し元や関数に依存している場合はインライン展開できません。なぜなら、コードは関数のない場所に配置されている可能性があるからです。

読む:http://whereswalden.com/2010/09/08/new-es5-strict-mode-support-now-with-poison-pills/

+0

記事が「tl; dr」で始まるのはなぜですか?私はそれが一般的に意味するものは知っていますが、この文脈ではありません。 –

+0

@Simeまあ、彼の記事は基本的にテキストの一つの巨大な壁であるという事実について著者がちょうどジョークを作っていると思うよ。 –

+0

ああ、そのあとジョーク。それはおそらくそれです。 –

1

あなたはそれを検討している場合、私は言うことができないので、それはあなたが単にオブジェクトリテラルに関数に名前を指定した場合、あなたはそれにその方法を参照することができ、指摘価値があります:

obj = { 
    foo : function METHODNAME() { 
     var myName = getMethodName(obj, METHODNAME); // "foo" 
    } 
} 

しかし、注意してください:私は、IEはこれが(というだけで、その関数にそれがアクセスできるより)囲みスコープにMETHODNAMEという名前の関数を定義するリリースバージョンにバグがあると思います。しかし、仕様によって、これは完全に正当なものであり、関数自体のどこにも見つからない名前を使用する限り、または関数がevalを呼び出すことができる場合はevalに渡されるコードを使用する限り、完全に正常に動作します。

+0

しかし、私はしたいと思います addEventListener( "event"、myfun.bind(this)); このリスナーをどこかに保存せずに削除することはできません。 myfun.bind()は新しい関数を返します。 これはスーパーラメです。 –

+0

それは正しいと思う。私は "スーパーラメ"は見る人の目の前にあると思うが、それは言語とAPIの仕組みだ。それ以外はどうすればいい?与えられたGCの振る舞い(弱参照のような振る舞い)を公開したくないということを考えると、複数のリスナーの間であいまいになっている、以前に追加したリスナーを削除する方法が必要です。自然な方法を削除する参照を指定して削除されていませんか?おそらく少し厄介ですが、私はより良い方法を見ていません。 –

+0

これは、arguments.calleeを使うとうまくいっています。引数は、関数なしで何も失わないということです。私は実際にあなたが何かを失うことを言っている、なぜならあなたはいつもその関数に名前をつけることができないからです。だから今私は、厳密なモードを無効にするか、これらのイベントリスナをすべて手動で追跡するという煩わしさ(および潜在的なリーク)を被るかを選択する必要があります。 –

関連する問題