Ответы:
typeof callback === "function"
Все текущие ответы используют литеральную строку, которую я предпочитаю не использовать в своем коде, если это возможно, - это не так (и обеспечивает ценное семантическое значение для загрузки):
function isFunction(possibleFunction) {
return typeof(possibleFunction) === typeof(Function);
}
Лично я стараюсь уменьшить количество строк, которые висят в моем коде ...
Кроме того, пока я знаю, что typeof это оператор, а не функция, использование синтаксиса делает его вредным для последнего.
isFunction(not_defined))где not_definedимя функции, которая не определена, и FireBug вернул, not_defined is not definedчто является правильным, но ваша функция должна возвращать false и не генерировать ошибку ...
not_defined, чтобы передать его значение, isFunction()и не может его разрешить. Ничто не может быть сделано для определения isFunction()этой проблемы.
isFunctionи делайте просто (typeof no_function == typeof Function).
typeof(Function())потому что Function - это функция; но так же как Array, Object и другие встроенные прототипы (из-за отсутствия лучшего термина). Если бы вы проверяли массив, вы бы не использовали его, typeof(array) === typeof(Array)например; вы будете использовать, typeof(array) === typeof(Array())потому что вам действительно нужно оценить функцию, если вы будете осторожны и последовательны.
if (callback && typeof(callback) == "function")
Обратите внимание , что обратный вызов (сам по себе) принимает значение , falseесли оно undefined, null, 0, или false. По сравнению с nullявляется слишком конкретным.
callbackсамо значение равно false-y, то его typeof никогда не может быть «функцией».
Эти методы, чтобы определить, реализована ли функция, также завершаются ошибкой, если переменная не определена, поэтому мы используем что-то более мощное, которое поддерживает получение строки:
function isFunctionDefined(functionName) {
if(eval("typeof(" + functionName + ") == typeof(Function)")) {
return true;
}
}
if (isFunctionDefined('myFunction')) {
myFunction(foo);
}
typeof window.doesthisexistвместо doesthisexist. Однако использование eval (которое: является злом), как показано, будет работать только с именованными функциями - это не будет работать с вариантом использования в вопросе.
Новое в JavaScript Я не уверен, изменилось ли поведение, но решение, данное Джейсоном Бантингом (6 лет назад), не будет работать, если возможная функция не определена.
function isFunction(possibleFunction) {
return (typeof(possibleFunction) == typeof(Function));
}
Это вызовет ReferenceError: possibleFunction is not definedошибку, когда движок попытается разрешить символ возможной функции (как указано в комментариях к ответу Джейсона).
Чтобы избежать такого поведения, вы можете только передать имя функции, которую вы хотите проверить, если она существует. Так
var possibleFunction = possibleFunction || {};
if (!isFunction(possibleFunction)) return false;
Это устанавливает переменную либо как функцию, которую вы хотите проверить, либо как пустой объект, если она не определена, что позволяет избежать проблем, упомянутых выше.
Пытаться:
if (typeof(callback) == 'function')
if ('function' === typeof callback) ...
if(typeof Function === typeof callback)...? :)
typeofпозже возвращает что-то другое (может быть, «Function» вместо «function») из-за новой / другой реализации JavaScript - кажется, что это будет менее вероятно, что новая / другая реализация сломает typeof Function === typeof callbackпроверку, потому что она должна быть одинаковой на семантическом уровне.
typeof(callback) == "function"
Я мог бы сделать
try{
callback();
}catch(e){};
Я знаю, что есть принятый ответ, но никто не предложил это. Я не совсем уверен, соответствует ли это описанию idiomatic, но это работает для всех случаев.
В более новых движках JavaScript finallyвместо них можно использовать.
typeof callbackлюбом случае.
accepted_types.indexOf(typeof value) !== -1ли он в диапазоне типов. В этой ситуации исключения были бы непомерными, на мой взгляд.
Попробуй это:
callback instanceof Function
Если вы используете http://underscorejs.org , у вас есть: http://underscorejs.org/#isFunction
_.isFunction(callback);
Если 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();
}
}
Ограничение состоит в том, что он всегда будет выполнять аргумент обратного вызова, хотя он не определен.
Для глобальных функций вы можете использовать это вместо 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также, но afaik. значение 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, но они делают почти то же самое.
Большинство, если не все предыдущие ответы имеют побочные эффекты для вызова функции
здесь лучшая практика
у тебя есть функция
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');
Если вы хотите переопределить функции, лучше всего использовать переменные функций, которые определены в порядке их появления, поскольку функции определяются глобально, независимо от того, где они происходят.
Пример создания новой функции, которая вызывает предыдущую функцию с тем же именем:
A=function() {...} // first definition
...
if (typeof A==='function')
oldA=A;
A=function() {...oldA()...} // new definition
Это сработало для меня
if( cb && typeof( eval( cb ) ) === "function" ){
eval( cb + "()" );
}
Однолинейное решение:
function something_cool(text, callback){
callback && callback();
}