web-dev-qa-db-ja.com

JavaScript関数が定義されているかどうかを確認する方法

JavaScriptの関数が定義されているかどうかはどのようにわかりますか?

このようなことをしたい

function something_cool(text, callback) {
    alert(text);
    if( callback != null ) callback();
}

しかし、それは私を取得します

コールバックは関数ではありません

コールバックが定義されていない場合のエラー。

278
Aaron Lee
typeof callback === "function"
431
Tom Ritter

現在の回答はすべてリテラル文字列を使用していますが、可能な場合はコードに含めない方がよいでしょう-これはそうではありません(そして、起動するために価値のある意味を提供します):

function isFunction(possibleFunction) {
  return typeof(possibleFunction) === typeof(Function);
}

個人的には、コードにぶら下がる文字列の数を減らすようにしています...


また、typeofは演算子であり、関数ではないことを認識していますが、後者として表示される構文を使用してもほとんど害はありません。

230
Jason Bunting
if (callback && typeof(callback) == "function")

コールバックは、falseundefined0、またはnullの場合、(それ自体で)falseに評価されることに注意してください。 nullとの比較は非常に具体的です。

15

変数が定義されていない場合、関数が実装されているかどうかを判断するメソッドも失敗するため、文字列の受信をサポートするより強力なものを使用しています。

function isFunctionDefined(functionName) {
    if(eval("typeof(" + functionName + ") == typeof(Function)")) {
        return true;
    }
}

if (isFunctionDefined('myFunction')) {
    myFunction(foo);
}
7
patriciorocca

JavaScriptを初めて使用した場合、動作が変更されたかどうかはわかりませんが、Jason Bunting(6年前)によって提供されたソリューションは、possibleFunctionが定義されていないと機能しません。

function isFunction(possibleFunction) {
  return (typeof(possibleFunction) == typeof(Function));
}

エンジンがシンボルpossibleFunctionを解決しようとすると、これはReferenceError: possibleFunction is not definedエラーをスローします(Jasonの答えへのコメントで述べたように)

この動作を回避するには、存在するかどうかを確認する関数の名前のみを渡すことができます。そう

var possibleFunction = possibleFunction || {};
if (!isFunction(possibleFunction)) return false;

これにより、変数がチェックする関数または定義されていない場合は空のオブジェクトに設定され、上記の問題が回避されます。

6
NectarSoft

試してください:

if (typeof(callback) == 'function')
5
bdukes

するかもしれない

try{
    callback();
}catch(e){};

受け入れられた答えがあることは知っていますが、誰もこれを提案しませんでした。これがイディオムの説明に当てはまるかどうかはわかりませんが、すべての場合に有効です。

新しいJavaScriptエンジンでは、代わりにfinallyを使用できます。

4
Quentin Engles
if ('function' === typeof callback) ...
4
Andrew Hedges
function something_cool(text, callback){
    alert(text);
    if(typeof(callback)=='function'){ 
        callback(); 
    };
}
3
ConroyP

これを試して:

callback instanceof Function
2
eWolf

試してください:

if (!(typeof(callback)=='undefined')) {...}
2
Brian

言及されているライブラリ@Venkat Sudheer Reddy Aedamaの source underscorejsを見ると、これを見ることができます。

_.isFunction = function(obj) {
  return typeof obj == 'function' || false;
};

これはちょうど私のヒントです、ヒントの答え:>

2
VentyCZ

http://underscorejs.org を使用すると、次のようになります。 http://underscorejs.org/#isFunction

_.isFunction(callback);

JQuery関数が定義されているかどうかを確認する方法を探していましたが、簡単に見つかりませんでした。

おそらくそれが必要かもしれません;)

if(typeof jQuery.fn.datepicker !== "undefined")
1
miguelmpn

関数を再定義する場合は、関数はどこで発生してもグローバルに定義されるため、関数変数は発生順に定義されるのが最適です。

同じ名前の以前の関数を呼び出す新しい関数を作成する例:

A=function() {...} // first definition
...
if (typeof A==='function')
   oldA=A;
A=function() {...oldA()...} // new definition
0
David Spector

グローバル関数の場合、回答の1つで提案されているevalの代わりにこれを使用できます。

var global = (function (){
    return this;
})();

if (typeof(global.f) != "function")
    global.f = function f1_shim (){
        // commonly used by polyfill libs
    };

global.f instanceof Functionも使用できますが、わかりません。 Functionの値はフレームごとに異なるため、単一フレームアプリケーションでのみ適切に機能します。そのため、通常は代わりにtypeofを使用します。環境によっては、typeof fにも異常がある場合があることに注意してください。 MSIE 6-8では、たとえばalertなどの一部の関数には「オブジェクト」タイプがありました。

ローカル関数によって、受け入れられた回答にあるものを使用できます。関数がローカルかグローバルかをテストすることもできます。

if (typeof(f) == "function")
    if (global.f === f)
        console.log("f is a global function");
    else
        console.log("f is a local function");

質問に答えるために、サンプルコードは最新のブラウザでエラーなく動作しているので、何が問題なのかわかりません。

function something_cool(text, callback) {
    alert(text);
    if( callback != null ) callback();
}

注:callback !== undefinedの代わりにcallback != nullを使用しますが、ほとんど同じです。

0
inf3rno

すべてではないにしても、ほとんどの以前の回答には、関数を呼び出す副作用があります

ここでベストプラクティス

あなたには機能があります

function myFunction() {
        var x=1;
    }
//direct way
        if( (typeof window.myFunction)=='function')
            alert('myFunction is function')
        else
            alert('myFunction is not defined');
//byString
        var strFunctionName='myFunction'
        if( (typeof window[strFunctionName])=='function')
            alert(s+' is function');
        else
            alert(s+' is not defined');
0
TexWiller

関数で一度だけではなくcallback()を呼び出す場合、再利用のために引数を初期化できます。

callback = (typeof callback === "function") ? callback : function(){};

例えば:

function something_cool(text, callback) {
    // Initialize arguments
    callback = (typeof callback === "function") ? callback : function(){};

    alert(text);

    if (text==='waitAnotherAJAX') {
        anotherAJAX(callback);
    } else {
        callback();
    }
}

制限は、定義されていなくても常にコールバック引数を実行することです。

0
Nick Tsai