1. ホーム
  2. javascript

[解決済み] JavaScriptで他の関数の中に関数を定義する

2023-02-02 19:19:45

質問

function foo(a) {
    if (/* Some condition */) {
        // perform task 1
        // perform task 3
    }
    else {
        // perform task 2
        // perform task 3
    }
}

上記のような構造を持つ関数があります。私は抽象化したい タスク3 を関数に変換したい。 bar() の範囲内だけに制限したいのですが、この関数のアクセスは foo(a) .

私の望むことを実現するためには、以下のように変更するのが正しいのでしょうか?

function foo(a) {
    function bar() {
        // Perform task 3
    }

    if (/* Some condition */) {
        // Perform task 1
        bar();
    }
    else {
        // Perform task 2
        bar();
    }
}

もし上記が正しいのであれば bar() は毎回再定義されるのでしょうか? foo(a) が呼ばれるたびに再定義されるのでしょうか?(私はここでCPUリソースの浪費を心配しています)。

どのように解決するのですか?

はい、あなたがそこに持っているものは正しいです。いくつかの注意点があります。

  • bar は、関数 foo が、しかし
    • モダンブラウザでは、これは非常に高速な処理です。(エンジンによっては コード を一度コンパイルするだけで、毎回異なるコンテキストでそのコードを再利用するエンジンもあります。Google の V8 エンジン(Chrome など)はほとんどの場合そうなっています)。
    • そして、何によって bar が何をするかによって、いくつかのエンジンはそれを "inline" できると判断して、関数呼び出しを完全に排除することができます。V8 はそうしていますし、そうしている唯一のエンジンではないはずです。当然ながら、コードの動作を変更しない場合にのみ、これを行うことができます。
  • を持つことによるパフォーマンスへの影響(もしあれば)。 bar が毎回作成されることによるパフォーマンスへの影響は、 JavaScript エンジンによって大きく異なります。もし bar が些細なものであれば、検出できないものからかなり小さなものまで様々でしょう。もしあなたが foo を何千回も続けて呼んでいるのでなければ (たとえば mousemove ハンドラから)、私はそれを心配しません。たとえそうであっても、遅いエンジンで問題が見られたときだけ心配することにします。 DOM 操作を含むテストケースは次のとおりです。 これは、影響があることを示唆していますが、些細なものです (おそらく DOM に関するものによって洗い流されたのでしょう)。 純粋な計算を行うテスト ケースは次のとおりです。 では、より大きな影響があることがわかりますが、率直に言って、その差は マイクロ マイクロ

    1 秒の違いです。 秒の違いであり、92% の増加でも <マイクロ マイクロ 秒かかるものに対して 92% の増加であっても、非常に高速です。実際の影響を見るまでは、または見ない限り、心配することはありません。

  • bar は関数内からしかアクセスできず、その関数を呼び出すためのすべての変数と引数にアクセスできます。このため、これは非常に便利なパターンです。
  • 関数を使用しているため 宣言 を使用しているため、宣言をどこに置いても (上、下、または中央 - 関数のトップレベルである限り、フロー制御文の中でない限り、これは構文エラーです)、ステップワイズコードの最初の行が実行される前に定義されることに留意してください。