详解JS: reduce方法实现 webpack多文件入口


Posted in Javascript onFebruary 14, 2017

1. reduce 方法介绍

1.1 简单场景

reduce 函数的设计意图就是方便进行叠加运算:

var arr = [0, 1, 2, 3];

// reduce 实现累加
var total = arr.reduce(function (pre, cur){
 return pre + cur;
}, 0);

console.log(total);  // 6

上述代码中,reduce 方法有两个参数,第一个参数是一个 callback,用于进行计算的函数;第二个参数则是累加计算的初始值: 0

reduce 以 0 作为初始值,从数组第 0 项开始累加,上述代码的计算过程如下:

total = 0;    // => 0
total = 0 + 0;  // => 0
total = 0 + 1;  // => 1
total = 1 + 2;  // => 3
total = 3 + 3;  // => 6

若不设置初始值 0,则 reduce 以数组第 0 项作为初始值,从第 1 项开始累加,其计算过程如下:

total = 0;    // => 0
total = 0 + 1;  // => 1
total = 1 + 2;  // => 3
total = 3 + 3;  // => 6

可以看出,reduce 函数根据初始值 0,不断进行叠加,完成最简单的数组累加。

1.2 两种简单的运用场景

第一个 demo,使用 reduce 函数进行二维数组的拼接:

var arr = [ [0], [1, 2], [3, 4, 5] ];

// reduce 实现数组拼接
var result = arr.reduce(function (pre, cur){
 return pre.concat(cur);
}, []);

console.log(result);  // [0, 1, 2, 3, 4, 5]

第二个 demo,使用 reduce 函数构造 JSON 数组:

// 此例演示:将所有员工的姓名进行拆分
var staff = ['Bob Dell', 'Johon Jobs', 'Maria July'];

// reduce 构造 JSON 数组
var result = staff.reduce(function (arr, full_name){
 arr.push({
  first_name: full_name.split(' ')[0],
  last_name: full_name.split(' ')[1]
 });

 return arr;
}, []);

console.log(JSON.stringify(result));
// [{"first_name":"Bob","last_name":"Dell"},{"first_name":"Johon","last_name":"Jobs"},{"first_name":"Maria","last_name":"July"}]

灵活使用 reduce 函数,能为我们节省不少中间变量和代码。

2. 用于实现 webpack 多文件入口配置

webpack 配置项中entry参数用于配置入口文件路径,通常对于只打包一个目录下的文件,只需要遍历该目录,构造一个如下的对象传递给entry即可:

// 注:index.js 为每个页面的入口文件,所有页面均在 ./fe/pages/ 目录下
var entry = {
 index: './fe/pages/home/index.js',
 list: './fe/pages/list/index.js'
};

通常,我们使用 reduce 方法来遍历同一目录下的入口:

var fs = require('fs');
var path = require('path');
...

// 定义入口路径
var entryPath = './fe/pages';

// 遍历路径下多文件入口
var entris = fs.readdirSync(entryPath).reduce(function (o, filename) {
 !/\./.test(filename) &&
 (o[filename] = './' + path.join(entryPath, filename, 'index.js'));
 return o;
}, {});

// entry = {
//  index: './fe/pages/home/index.js',
//  list: './fe/pages/list/index.js'
// }

对于多页面应用的开发场景,也许会需要构造类似于下面这样的一个对象:

// 多个入口,页面、公共组件并不一定在同一个目录下
var entry = {
 index: './fe/pages/home/index.js',
 list: './fe/pages/list/index.js',
 header: './fe/components/header/index.js',
 footer: './fe/components/footer/index.js'
};

可以发现,我们要打包的页面、公共组件不一定在同一个目录下,这时候就需要对原先的方法进行扩展,见代码:

var fs = require('fs');
var path = require('path');
...

// 定义入口路径
var entryPath = ['./fe/pages', './fe/components'];

// 遍历路径下多文件入口
var mkEntriesMap = function (entryPath){
 if (typeof(entryPath) == 'string') {  // 若 entryPath 为字符串,则直接遍历此目录
  var path_map = fs.readdirSync(entryPath).map(function (filename){
   return filename + '::./' + path.join(entryPath, filename, 'index.js');
  });
 } else if (typeof(entryPath) == 'object') {  // 若 entryPath 为数组,则进行两级遍历
  var path_map = entryPath.map(function (entry){
   return fs.readdirSync(entry).map(function (filename){
    return filename + '::./' + path.join(entry, filename, 'index.js');
   });
  }).reduce(function (preArr, curArr){
   return preArr.concat(curArr);
  }, []);
 } else {
  throw 'Type of config.entryPath is not valid.';
  return;
 }

 return path_map.reduce(function (o, file_map){
  var file_name = file_map.split('::')[0];
  var file_path = file_map.split('::')[1];

  if (!/\./.test(file_name)) {
   o[file_name] = file_path;
  }

  return o;
 }, {});
};

// 构造对象
var entris = mkEntriesMap(entryPath);

// entry = {
//  index: './fe/pages/home/index.js',
//  list: './fe/pages/list/index.js',
//  header: './fe/components/header/index.js',
//  footer: './fe/components/footer/index.js'
// }

这样做的好处在于,只需配置一开始的entryPath就行了,同时支持单个或多个路径下的文件打包:

// entryPath 可以为一个字符串
var entryPath = './fe/pages';

// entryPath 也可以设为一个数组
var entryPath = ['./fe/pages', './fe/components'];

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
不同Jquery版本引发的问题解决
Oct 14 Javascript
JS图片自动轮换效果实现思路附截图
Apr 30 Javascript
详解JSON1:使用TSQL查询数据和更新JSON数据
Nov 21 Javascript
JavaScript仿微信打飞机游戏
Jul 05 Javascript
vue获取DOM元素并设置属性的两种实现方法
Sep 30 Javascript
基于JavaScript+HTML5 实现打地鼠小游戏逻辑流程图文详解(附完整代码)
Nov 02 Javascript
angular4 JavaScript内存溢出问题
Mar 06 Javascript
关于jquery layui弹出层的使用方法
Apr 21 jQuery
对vue 键盘回车事件的实例讲解
Aug 25 Javascript
vuejs点击class变化的实例
Sep 05 Javascript
详解基于Vue,Nginx的前后端不分离部署教程
Dec 04 Javascript
Vue this.$router.push(参数)实现页面跳转操作
Sep 09 Javascript
如何快速上手Vuex
Feb 14 #Javascript
BootStrap框架中的data-[ ]自定义属性理解(推荐)
Feb 14 #Javascript
Easyui Tree获取当前选择节点的所有顶级父节点
Feb 14 #Javascript
Vue组件开发初探
Feb 14 #Javascript
JavaScript Base64 作为文件上传的实例代码解析
Feb 14 #Javascript
JavaScript实现定时页面跳转功能示例
Feb 14 #Javascript
javaScript嗅探执行神器-sniffer.js
Feb 14 #Javascript
You might like
星际争霸, 教主第一视角, ZvT经典龙蛇演义
2020/03/02 星际争霸
Godaddy空间Zend Optimizer升级方法
2010/05/10 PHP
PHP面向对象编程之深入理解方法重载与方法覆盖(多态)
2015/12/24 PHP
在Laravel框架里实现发送邮件实例(邮箱验证)
2016/05/20 PHP
bindParam和bindValue的区别以及在Yii2中的使用详解
2018/03/12 PHP
根据分辨率不同,调用不同的css文件
2006/07/07 Javascript
过虑特殊字符输入的js代码
2010/08/05 Javascript
纯JS实现的批量图片预览加载功能
2011/08/14 Javascript
jQuery使用技巧简单汇总
2013/04/18 Javascript
Javascript 遮罩层和加载效果代码
2013/08/01 Javascript
Knockout数组(observable)使用详解示例
2013/11/15 Javascript
BootstrapTable+KnockoutJS自定义T4模板快速生成增删改查页面
2016/08/01 Javascript
jQuery的extend方法【三种】
2016/12/14 Javascript
微信小程序 使用canvas制作K线实例详解
2017/01/12 Javascript
JavaScript 事件对内存和性能的影响
2017/01/22 Javascript
通过npm引用的vue组件使用详解
2017/03/02 Javascript
在React中写一个Animation组件为组件进入和离开加上动画/过度效果
2019/06/24 Javascript
Nodejs在局域网配置https访问的实现方法
2020/10/17 NodeJs
解决antd的Form组件setFieldsValue的警告问题
2020/10/29 Javascript
Python3实现发送QQ邮件功能(附件)
2020/12/23 Python
python 从csv读数据到mysql的实例
2018/06/21 Python
pandas 根据列的值选取所有行的示例
2018/11/07 Python
Python脚本修改阿里云的访问控制列表的方法
2019/03/08 Python
python3.6下Numpy库下载与安装图文教程
2019/04/02 Python
django的settings中设置中文支持的实现
2019/04/28 Python
python GUI实现小球满屏乱跑效果
2019/05/09 Python
python 绘制拟合曲线并加指定点标识的实现
2019/07/10 Python
Python HTMLTestRunner库安装过程解析
2020/05/25 Python
html5画布旋转效果示例
2014/01/27 HTML / CSS
HealthElement海外旗舰店:新西兰大卖场
2018/02/23 全球购物
Java里面StringBuilder和StringBuffer有什么区别
2016/06/06 面试题
linux面试题参考答案(2)
2015/12/06 面试题
自动化专业职业生涯规划书范文
2014/01/16 职场文书
个人主要事迹材料
2014/08/26 职场文书
大学新生军训自我鉴定范文
2014/09/13 职场文书
市场部经理岗位职责
2015/02/02 职场文书