Underscore源码解析

Underscore源码解析


前言

Underscore是一个JavaScript工具库,它提供了许多操作集合、数组、函数等的实用函数。简单说它集成了好多工具函数,不用自己写一些常用的函数了。

准备

软件 描述
git 代码管理工具

步骤

克隆代码到本地:

 git clone https://github.com/jashkenas/underscore.git

查看目录结构:
Underscore源码解析_第1张图片

从目录结构中可以看到,只有一个docs(文档)和test(测试)目录,然后看下根目录下,可以推测源码文件就一个underscore.js文件(min文件是压缩文件)

查看package.json文件(TODO:package.json文件解析):
Underscore源码解析_第2张图片

简单看下项目的依赖(devDependencies)和 scripts,大致了解下项目构建,怎么打包。可以知道构建是通过如下脚本(主要是minify插件对源码压缩)执行的:

npm run minify -- --source-map --source-map-url \" \" -o underscore-min.js

查看源码:
1、首先收拢代码(不要被代码量吓到),可以看到所有的代码都放到一个闭包里面,里面是一个立即执行的函数。
Underscore源码解析_第3张图片

2、展开闭包函数,可以看到首先是全局变量的声明。
Underscore源码解析_第4张图片

// Baseline setup
  // --------------

  // Establish the root object, `window` (`self`) in the browser, `global`
  // on the server, or `this` in some virtual machines. We use `self`
  // instead of `window` for `WebWorker` support.
  var root = typeof self == 'object' && self.self === self && self ||
            typeof global == 'object' && global.global === global && global ||
            this ||
            {};// 获取全部变量

  // Save the previous value of the `_` variable.
  var previousUnderscore = root._;

  // Save bytes in the minified (but not gzipped) version:
  var ArrayProto = Array.prototype, ObjProto = Object.prototype; // 保存js引擎的数组和对象的原型
  var SymbolProto = typeof Symbol !== 'undefined' ? Symbol.prototype : null;

  // Create quick reference variables for speed access to core prototypes.
  var push = ArrayProto.push,
      slice = ArrayProto.slice,
      toString = ObjProto.toString,
      hasOwnProperty = ObjProto.hasOwnProperty;// 保存js引擎的原型方法

  // All **ECMAScript 5** native function implementations that we hope to use
  // are declared here.
  var nativeIsArray = Array.isArray,
      nativeKeys = Object.keys,
      nativeCreate = Object.create;

  // Naked function reference for surrogate-prototype-swapping.
  var Ctor = function(){};

  // Create a safe reference to the Underscore object for use below.
  var _ = function(obj) {
    if (obj instanceof _) return obj;
    if (!(this instanceof _)) return new _(obj);// 确保全局对象 _ 被安全创建
    this._wrapped = obj;
  };

  // Export the Underscore object for **Node.js**, with
  // backwards-compatibility for their old module API. If we're in
  // the browser, add `_` as a global object.
  // (`nodeType` is checked to ensure that `module`
  // and `exports` are not HTML elements.)
  if (typeof exports != 'undefined' && !exports.nodeType) {
    if (typeof module != 'undefined' && !module.nodeType && module.exports) {
      exports = module.exports = _;
    }
    exports._ = _;
  } else {
    root._ = _;
  }// 暴露全局对象 _ (所有的方法和属性都在_里面)

  // Current version.
  _.VERSION = '1.9.1'; // 版本信息

3、在全局对象上添加方法
Underscore源码解析_第5张图片

可以看到在全局对象_上添加了许多方法map、reduce、……….,这些方法的Api介绍官网都有,这里就不多说了。

4、函数调试解析,一般方法通过名称就可以知道它的作用,但是想了解内部实现的话可以通过调试。(TODO)

你可能感兴趣的:(前端(js,mvvm))