推荐答案
使用 typeof
操作符和 instanceof
操作符都可以判断一个变量是否为函数。
方法一: typeof
操作符
-- -------------------- ---- ------- -------- ------------ -- ----- --------------- - -- -- --- ----- -------- - --- ----- -------- - -------- ------------------ ---------- --- ------------ -- ---- ------------------ --------------- --- ------------ -- ---- ------------------ -------- --- ------------ -- ----- ------------------ -------- --- ------------ -- -----
typeof
操作符对于函数会返回 'function'
字符串,这是最常用且最直接的判断方法。
方法二: instanceof
操作符
-- -------------------- ---- ------- -------- ------------ -- ----- --------------- - -- -- --- ----- -------- - --- ----- -------- - -------- ---------------------- ---------- ---------- -- ---- --------------------------- ---------- ---------- -- ---- -------------------- ---------- ---------- -- ----- -------------------- ---------- ---------- -- ----- ----- ------- -- ------------------- ---------- ---------- -- ----
instanceof
操作符用于检测构造函数的 prototype
属性是否出现在某个实例对象的原型链上。函数本身也是对象,所以是 Function
的实例。
本题详细解读
typeof
操作符的优势和局限性
- 优势:
- 简单快捷,是判断基本类型的常用方法。
- 对于
function
类型,直接返回'function'
字符串,方便直接判断。
- 局限性:
- 无法区分对象和函数对象,例如,对于
class
,typeof MyClass === 'function'
返回true
,但是它不仅仅是一个简单的函数,所以typeof
仅适合粗略判断。
- 无法区分对象和函数对象,例如,对于
instanceof
操作符的优势和局限性
- 优势:
- 可以判断对象是否为某个构造函数的实例。
- 可以判断继承关系。
- 局限性:
- 需要知道构造函数,不适用于直接的字面量函数,如
const myFunc = function(){}
。 - 在跨 iframe 或多窗口环境下可能会出错,因为每个 iframe 都有自己的全局环境和 Function 构造函数。
- 需要知道构造函数,不适用于直接的字面量函数,如
选择建议
- 如果仅仅是判断一个变量是否是可执行的函数,推荐使用
typeof
操作符。 - 如果需要判断更详细的实例关系,比如判断是否是某个特定构造函数的实例,可以使用
instanceof
操作符。 - 大部分场景下,
typeof
操作符=== 'function'
足够满足需求。
补充: 使用 Object.prototype.toString.call()
虽然不常用,但 Object.prototype.toString.call()
也可以判断一个变量是否为函数:
-- -------------------- ---- ------- -------- ------------ -- ----- --------------- - -- -- --- ----- -------- - --- ----- -------- - -------- ------------------------------------------------------ --- -------- ------------ -- ---- ----------------------------------------------------------- --- -------- ------------ -- ---- ---------------------------------------------------- --- -------- ---------- -- ---- ---------------------------------------------------- --- -------- ---------- -- ----
这个方法更通用,可以判断所有数据类型,但对于判断函数略显繁琐,不如 typeof
直观高效。