检测一个函数是否是JavaScript原生函数的小技巧


Posted in Javascript onMarch 13, 2015

在我的开发工作中经常会遇到需要判断一个函数是否是JavaScript原生函数的情况,有时候这是一个很必要的工作,你需要知道这个函数是浏览器自身提供的,还是由第三方封装、伪装成原生函数。当然,最好的方法是考察执行这个函数的toString方法的返回值。

The JavaScript

完成这个任务的方法非常简单:

function isNative(fn) {

 return (/\{\s*\[native code\]\s*\}/).test('' + fn);

}

toString方法会返回这个方法的字符串形式,然后用正则表达式判断里面包含的字符。

更强悍的方法

Lodash的创始人John-David Dalton找到了一个更佳的方案:

;(function() {
  // Used to resolve the internal `[[Class]]` of values

  var toString = Object.prototype.toString;

  

  // Used to resolve the decompiled source of functions

  var fnToString = Function.prototype.toString;

  

  // Used to detect host constructors (Safari > 4; really typed array specific)

  var reHostCtor = /^\[object .+?Constructor\]$/;
  // Compile a regexp using a common native method as a template.

  // We chose `Object#toString` because there's a good chance it is not being mucked with.

  var reNative = RegExp('^' +

    // Coerce `Object#toString` to a string

    String(toString)

    // Escape any special regexp characters

    .replace(/[.*+?^${}()|[\]\/\\]/g, '\\$&')

    // Replace mentions of `toString` with `.*?` to keep the template generic.

    // Replace thing like `for ...` to support environments like Rhino which add extra info

    // such as method arity.

    .replace(/toString|(function).*?(?=\\\()| for .+?(?=\\\])/g, '$1.*?') + '$'

  );

  

  function isNative(value) {

    var type = typeof value;

    return type == 'function'

      // Use `Function#toString` to bypass the value's own `toString` method

      // and avoid being faked out.

      ? reNative.test(fnToString.call(value))

      // Fallback to a host object check because some environments will represent

      // things like typed arrays as DOM methods which may not conform to the

      // normal native pattern.

      : (value && type == 'object' && reHostCtor.test(toString.call(value))) || false;

  }

  

  // export however you want

  module.exports = isNative;

}());

现在你也看到了,很复杂,但更强大。当然,这不是为了做安全防护,它只是给你提供是否是原生函数的相关信息。
Javascript 相关文章推荐
在Javascript中为String对象添加trim,ltrim,rtrim方法
Sep 22 Javascript
JS解析XML的实现代码
Nov 12 Javascript
JQuery右键菜单插件ContextMenu使用指南
Dec 19 Javascript
AngularJS整合Springmvc、Spring、Mybatis搭建开发环境
Feb 25 Javascript
Bootstrap3学习笔记(二)之排版
May 20 Javascript
AngularJS ng-controller 指令简单实例
Aug 01 Javascript
老生常谈的跨域处理
Jan 11 Javascript
Vue2.x中的Render函数详解
May 30 Javascript
浅谈Webpack自动化构建实践指南
Dec 18 Javascript
如何在JavaScript中优雅的提取循环内数据详解
Mar 04 Javascript
如何在wxml中直接写js代码(wxs)
Nov 14 Javascript
json_decode 索引为数字时自动排序问题解决方法
Mar 28 Javascript
DOM操作一些常用的属性汇总
Mar 13 #Javascript
JavaScript获取页面上被选中文字的方法技巧
Mar 13 #Javascript
jQuery源码分析之Callbacks详解
Mar 13 #Javascript
JavaScript获取伪元素(Pseudo-Element)属性的方法技巧
Mar 13 #Javascript
Javascript定义类(class)的三种方法详解
Mar 13 #Javascript
JavaScript中5种调用函数的方法
Mar 12 #Javascript
JavaScript实现的一个倒计时的类
Mar 12 #Javascript
You might like
利用static实现表格的颜色隔行显示
2006/10/09 PHP
一个PHP数组应该有多大的分析
2009/07/30 PHP
关于Iframe如何跨域访问Cookie和Session的解决方法
2013/04/15 PHP
用php实现选择排序的解决方法
2013/05/04 PHP
PHP mysql事务问题实例分析
2016/01/18 PHP
PHP html_entity_decode()函数讲解
2019/02/25 PHP
javascript showModalDialog 多层模态窗口实现页面提交及刷新的代码
2009/11/28 Javascript
Array.prototype.concat不是通用方法反驳[译]
2012/09/20 Javascript
jQuery焦点图切换简易插件制作过程全纪录
2014/08/27 Javascript
node.js中的fs.fsyncSync方法使用说明
2014/12/15 Javascript
纯JS实现可拖拽表单的简单实例
2016/09/02 Javascript
深入对Vue.js $watch方法的理解
2017/03/20 Javascript
用Vue.extend构建消息提示组件的方法实例
2017/08/08 Javascript
zTree 树插件实现全国五级地区点击后加载的示例
2018/02/05 Javascript
详解webpack打包时排除其中一个css、js文件或单独打包一个css、js文件(两种方法)
2018/10/26 Javascript
Element-UI+Vue模式使用总结
2020/01/02 Javascript
JS代码检查工具ESLint介绍与使用方法
2020/02/04 Javascript
微信小程序单选框自定义赋值
2020/05/26 Javascript
Vuex的各个模块封装的实现
2020/06/05 Javascript
理解Python中的With语句
2016/03/18 Python
对Python 2.7 pandas 中的read_excel详解
2018/05/04 Python
详解Python的三种可变参数
2019/05/08 Python
Appium+python自动化怎么查看程序所占端口号和IP
2019/06/14 Python
解决pycharm 安装numpy失败的问题
2019/12/05 Python
Django单元测试中Fixtures用法详解
2020/02/25 Python
Django自定义全局403、404、500错误页面的示例代码
2020/03/08 Python
python的reverse函数翻转结果为None的问题
2020/05/11 Python
简单了解Python字典copy与赋值的区别
2020/09/16 Python
Fnac西班牙官网:法国文化和电子产品零售商
2021/03/14 全球购物
广州一家公司的.NET面试题
2016/06/11 面试题
XML文档定义有几种形式?它们之间有何本质区别?解析XML文档有哪几种方式?
2016/01/12 面试题
教师实习自我鉴定
2013/12/14 职场文书
副总经理任命书
2014/06/05 职场文书
作风整顿剖析材料
2014/09/30 职场文书
2015年体检中心工作总结
2015/05/27 职场文书
Java8 Stream API 提供了一种高效且易于使用的处理数据的方式
2022/04/13 Java/Android