详解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 相关文章推荐
实例代码详解javascript实现窗口抖动及qq窗口抖动
Jan 04 Javascript
javascript HTML5 Canvas实现圆盘抽奖功能
Apr 11 Javascript
jQuery EasyUI datagrid在翻页以后仍能记录被选中行的实现代码
Aug 15 Javascript
如何解决jQuery EasyUI 已打开Tab重新加载问题
Dec 19 Javascript
vue深入解析之render function code详解
Jul 18 Javascript
浅谈Node Inspector 代理实现
Oct 19 Javascript
浅谈vue-router2路由参数注意的问题
Nov 08 Javascript
Vue+webpack项目基础配置教程
Feb 12 Javascript
js实现图片上传即时显示效果
Sep 30 Javascript
vue使用prop可以渲染但是打印台报错的解决方式
Nov 13 Javascript
解决vue做详情页跳转的时候使用created方法 数据不会更新问题
Jul 24 Javascript
关于antd tree 和父子组件之间的传值问题(react 总结)
Jun 02 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
一个简单的php实现的MySQL数据浏览器
2007/03/11 PHP
php cookie的操作实现代码(登录)
2010/12/29 PHP
PHP 开发者该知道的 5 个 Composer 小技巧
2016/02/03 PHP
Yii数据库缓存实例分析
2016/03/29 PHP
php利用递归实现删除文件目录的方法
2016/09/23 PHP
php基于curl重写file_get_contents函数实例
2016/11/08 PHP
Yii框架的路由配置方法分析
2019/09/09 PHP
使用jQuery+HttpHandler+xml模拟一个三级联动的例子
2011/08/09 Javascript
javascript中scrollTop详解
2015/04/13 Javascript
基于jQuery实现的QQ表情插件
2015/08/25 Javascript
JS实现网页标题栏显示当前时间和日期的完整代码
2015/11/02 Javascript
JS中对象与字符串的互相转换详解
2016/05/20 Javascript
利用jQuery实现CheckBox全选/全不选/反选的简单代码
2016/05/31 Javascript
VC调用javascript的几种方法(推荐)
2016/08/09 Javascript
纯js三维数组实现三级联动效果
2017/02/07 Javascript
微信小程序 连续旋转动画(this.animation.rotate)详解
2017/04/07 Javascript
详解在Angularjs中ui-sref和$state.go如何传递参数
2017/04/24 Javascript
Bootstrap Table 在指定列中添加下拉框控件并获取所选值
2017/07/31 Javascript
详解javascript replace高级用法
2019/02/17 Javascript
vue总线机制(bus)知识点详解
2020/05/10 Javascript
[01:05:30]VP vs TNC 2018国际邀请赛小组赛BO2 第一场 8.17
2018/08/20 DOTA
python中split方法用法分析
2015/04/17 Python
python编程开发之日期操作实例分析
2015/11/13 Python
详解django中url路由配置及渲染方式
2019/02/25 Python
详解如何管理多个Python版本和虚拟环境
2019/05/10 Python
详解使用PyInstaller将Pygame库编写的小游戏程序打包为exe文件
2019/08/23 Python
Python上下文管理器用法及实例解析
2019/11/11 Python
Python列表切片常用操作实例解析
2019/12/16 Python
python实现时间序列自相关图(acf)、偏自相关图(pacf)教程
2020/06/03 Python
解决PyCharm不在run输出运行结果而不是再Console里输出的问题
2020/09/21 Python
校庆筹备方案
2014/03/30 职场文书
2014年信息宣传工作总结
2014/12/18 职场文书
产品质量保证书范本
2015/02/27 职场文书
杨善洲观后感
2015/06/04 职场文书
《巨人的花园》教学反思
2016/02/19 职场文书
用javascript制作qq注册动态页面
2021/04/14 Javascript