数组reduce函数,数组求和reduce
作为ES5中新的常规数组方法之一,reduce是一种强有力的方法。本文介绍了25数组化简的高级用法。
Reduce是ES5中新的常规数组方法之一。相比forEach、filter、map,实际使用中似乎忽略了一些。发现身边的人很少使用,导致这个强大的方法逐渐被埋没。
如果经常用reduce,怎么能这么轻易放过!我还是要把它从灰尘里拿出来擦干净,把它的高级用法呈现给大家。这么有用的方法不应该被大众埋没。
下面是对reduce语法的简要描述。具体可参考MDN中reduce()的相关描述。
定义:对数组中的每个元素执行一个自定义累加器,将其结果汇总成单个返回值形式:array.reduce((t,v,I,a)={},Init)参数callback:回调函数(必选)initValue: initValue(可选)参数total(t):累加器计算后的返回值(必选)value(v):当前元素(必选)010-必选index(必选用累加器处理V,累加V到T的映射结果,结束这个循环,返回T进入下一个循环,重复上述操作,直到数组的最后一个元素遍历完毕。返回最终treduce的本质是积累我们举个简单的栗子,看看reduce的计算结果。
const arr=[3,5,1,4,2];
const a=arr.reduce((t,v)=t v);
//相当于
const b=arr.reduce((t,v)=t v,0);
Reduce本质上是一个累加器函数,通过自定义累加器累加数组成员,得到一个由累加器生成的值。另外,reduce还有个弟弟,reduceRight。两种方法的功能其实是一样的,只是reduce按升序执行,reduceRight按降序执行。
对空数组调用reduce()和reduceRight()不会执行其回调函数。可以认为reduce()对于空数组是无效的
高级用法
仅凭上面这个简单的栗子不足以解释reduce是什么。为了展示reduce的魅力,我提供了25个场景来应用reduce的高级用法。一些高级用法可能需要与其他方法结合使用,这为reduce的多样化提供了更多的可能性。
有些示例代码可能写得有些粗俗。如果不习惯,可以整理成自己习惯的写法array。
函数累加(.vals
return vals.reduce((t,v)=t v,0);
}
函数乘法(.vals
return vals.reduce((t,v)=t * v,1);
}积累(1,2,3,4,5);//15
乘法(1,2,3,4,5);//120把上一次输出的值作为下一次输入的值
常数分数=[
{分数:90,科目:‘语文’,权重:0.5 },
{分数:95,科目:“数学”,权重:0.3 },
{分数:85,科目:“英语”,权重:0.2 }
];
const result=scores.reduce((t,v)=t v.score * v.weight,0);//90.5累加累乘
函数反转(arr=[]) {
return arr.reduceRight((t,v)=(t.push(v),t),[]);
}Reverse([1,2,3,4,5]);//[5, 4, 3, 2, 1]权重求和
const arr=[0,1,2,3];
//而不是映射:[0,2,4,6]
const a=arr . map(v=v * 2);
const b=arr.reduce((t,v)=[.t,v * 2],[]);
//而不是筛选器:[2,3]
const c=arr . filter(v=v 1);
const d=arr.reduce((t,v)=v 1?[.t,v] : t,[]);
//而不是映射和过滤器:[4,6]
const e=arr.map(v=v * 2)。滤波器(v=v 2);
const f=arr.reduce((t,v)=v * 2 2?[.t,v * 2] : t,[]);代替reverse
常数分数=[
{分数:45,主题:“中文”},
{分数:90,科目:“数学”},
{分数:60,科目:“英语”}
];
//而不是一些:至少有一个门是合格的
const isatleastonequalized=scores . reduce((t,v)=t v.score=60,false);//真
//而不是every: all限定
const isAllQualified=scores . reduce((t,v)=t v.score=60,true);//false代替map和filter
函数块(arr=[],size=1) {
返回长度是多少?arr.reduce((t,v)=(t[t.length - 1]).长度===大小?t.push([v]) : t[t.length - 1].push(v),t),[[]]):[];
}const arr=[1,2,3,4,5];
Chunk(arr,2);//[[1, 2], [3, 4], [5]]代替some和every
函数差(arr=[],oarr=[]) {
return arr.reduce((t,v)=(!oarr.includes(v) t.push(v),t),[]);
}const arr1=[1,2,3,4,5];
const arr2=[2,3,6]
差(arr1,arr 2);//[1, 4, 5]数组分割
函数填充(arr=[],val= ,start=0,end=arr.length) {
if(start 0 start=end end arr。长度)返回arrive)
返回[
.arr.slice(0,start),
.数组切片(开始,结束)。reduce((t,v)=(t.push(val v),t),[]),
.数组切片(结束,数组长度)
];
}const arr=[0,1,2,3,4,5,6];
Fill(arr, aaa ,2,5);//[0,1, aaa , aaa ,5,6]数组过滤
函数Flat(arr=[]) {
return arr.reduce((t,v)=t.concat(Array.isArray(v)?平(五) :五),[])
}const arr=[0,1,[2,3],[4,5,[6,7],[8,[9,10,[11,12]];
平坦(arr);//[0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12]数组填充
函数Uniq(arr=[]) {
return arr.reduce((t,v)=t.includes(v)?t : [.t,v],[]);
}const arr=[2,1,0,3,2,1,2];
uniq(arr);//[2, 1, 0, 3]数组扁平
函数Max(arr=[]) {
return arr.reduce((t,v)=t v?t:v);
}
函数Min(arr=[]) {
return arr.reduce((t,v)=t v?t:v);
}const arr=[12,45,21,65,38,76,108,43];
max(arr);//108
min(arr);//12数组去重
函数Unzip(arr=[]) {
return arr.reduce(
(t,v)=(v.forEach((w,i)=t[i]).push(w))、t),
Array.from({长度:Math.max(.arr.map(v=v.length)) }).映射(v=[])
);
} const arr=[ a ,1,true],[b ,2,false]];
解压(arr);//[[a , b],[1,2],[真,假]]数组最大最小值
函数计数(arr=[]) {
return arr.reduce((t,v)=(t[v]=(t[v] 0) 1,t),{ });
}const arr=[0,1,1,2,2,2];
计数(arr);//{ 0: 1, 1: 2, 2: 3 }此方法是字符统计和单词统计的原理,入参时把字符串处理成数组即可数组成员独立拆解
函数位置(arr=[],val) {
return arr.reduce((t,v,i)=(v===val t.push(i),t),[]);
}const arr=[2,1,5,4,2,1,6,6,7];
位置(arr,2);//[0, 4]数组成员个数统计
函数组(arr=[],key) {
回车键?arr.reduce((t,v)=(!t[v[key]] (t[v[key]]=[],t[v[key]].push(v),t),{ }):{ };
}常量数组=[
{地区:“GZ”,姓名: YZW ,年龄:27 },
{地区:“GZ”,姓名:“TYJ”,年龄:25 },
{地区: SZ ,姓名: AAA ,年龄:23 },
{面积: FS ,姓名: BBB ,年龄:21 },
{区域: SZ ,名称: CCC ,年龄:19 }
];//以地区区域作为分组依据
Group(arr, area );//{ GZ:数组(二)、SZ:数组(2),FS:数组(1) }数组成员位置记录
函数关键字(arr=[],keys=[]) {
return keys.reduce((t,v)=(arr。some(w=w . includes(v))t . push(v),t),[]);
}const text=[
今天天气真好,我想出去钓鱼,
我一边看电视,一边写作业,
小明喜欢同桌的小红,又喜欢后桌的小君,真铥花心,
最近上班喜欢摸鱼的人实在太多了,代码不好好写,在想入非非
];
常数关键字=[偷懒, 喜欢, 睡觉, 摸鱼, 真好, 一边, 明天];
关键词(文本,关键词);//[喜欢, 摸鱼, 真好, 一边]数组成员特性分组
函数ReverseStr(str=) {
返回str.split( ).reduceRight((t,v)=t v);
}const str=reduce最牛逼;
反向str(str);//逼牛最ecuder数组成员所含关键字统计
函数千分位数(数字=0) {
const str=( num).toString().拆分(.);
const int=nums=nums.split( ).反转()。reduceRight((t,v,i)=t (i % 3?v : `${v},`), ).replace(/^,,$/g,“);
const dec=nums=nums.split( ).reduce((t,v,i)=t ((i 1) % 3?v : `${v},`), ).replace(/^,,$/g,“);
return str.length 1?` ${int(str[0])} .$ { dec(str[1])} `:int(str[0]);
} ThousandNum(1234);//1,234
千分位数(1234.00);//1,234
千分位数(0.1234);//0.123,4
千分位数(1234.5678);//1,234.567,8字符串翻转
异步函数AsyncTotal(arr=[]) {
return arr.reduce(async(t,v)={
const at=await t;
const Todo=await Todo(v);
at[v]=todo;
返回时间:
},答应。解析({ });
}常数结果=await异步总计();//需要在异步非同步(异步)包围下使用数字千分化
函数Fibonacci(len=2) {
const arr=[.新数组(莱恩).keys()];
return arr.reduce((t,v,i)=(i 1 t.push(t[i - 1] t[i - 2]),t),[0,1]);
}斐波那契(10);//[0, 1, 1, 2, 3, 5, 8, 13, 21, 34]异步累计
函数ParseUrlSearch() {
返回location.search.replace(/(^\?)($)/g, ).拆分("")。减少((t,v)={
const [key,val]=v . split(=);
t[key]=decodeURIComponent(val);
return t;
}, {});
}//假设统一资源定位器为:https://www.baidu.com?年龄=25岁姓名=TYJ
ParseUrlSearch();//{年龄: 25 ,姓名: TYJ }斐波那契数列
函数StringifyUrlSearch(search={}) {
返回对象.条目(搜索)。减少(
(t,v)=` $ { t } $ { v[0]}=$ { encodeURIComponent(v[1])} `,
对象.键(搜索)。长度??:
).替换(/$/, );
}StringifyUrlSearch({年龄:27,姓名: YZW });//?age=27name=YZWURL参数反序列化
函数GetKeys(obj={},keys=[]) {
返回Object.keys(obj).减少((t,v)=(键。包括(v)(t[v]=obj[v]),t),{ });
}const target={ a: 1,b: 2,c: 3,d:4 };
常数关键字=[a , d ];
GetKeys(target,keyword);//{ a: 1,d: 4 }URL参数序列化
const people=[
{地区:“GZ”,姓名: YZW ,年龄:27 },
{地区: SZ ,姓名:“TYJ”,年龄:25 }
];
const map=people.reduce((t,v)={
const { name,rest }=v;
t[name]=rest;
return t;
}, {});//{ YZW: {…},TYJ: {…} }返回对象指定键值
函数合成(.funs) {
if (funs.length===0) {
返回arg=arg
}
if (funs.length===1) {
return funs[0];
}
return funs.reduce((t,v)=(.arg)=t(v(.arg)));
}
兼容和性能
好用是挺好用的,但是兼容性如何呢?在犬科动物上搜索一番,兼容性绝对的好,可大胆在任何项目上使用。不要吝啬你的想象力,尽情发挥减少的构成技能啦。对于时常做一些累计的功能,减少绝对是首选方法。
另外,有些同学可能会问,减少的性能又如何呢?下面我们通过对for、forEach、map和减少四个方法同时做1~100000的累加操作,看看四个方法各自的执行时间。
//创建一个长度为100000的数组
常量列表=[.新数组(100000)。keys()];
//对于
console.time(for ).
设结果1=0;
对于(设I=0;i list.lengthi ) {
结果1=11
}
console.log(结果1);
控制台。时间结束(“for”);
//forEach
console.time(forEach ).
设结果2=0;
列表。foreach(v=(结果2=v 1));
console.log(结果2);
控制台。时间结束(“forEach”);
//地图
控制台。时间(“地图”);
设结果3=0;
list.map(v=(result3=v 1,v));
console.log(结果3);
控制台。时间结束(“map”);
//减少
控制台。时间(减少);
const result4=list.reduce((t,v)=t v 1,0);
console.log(结果4);
控制台。时间结束( reduce );累加操作执行时间数组转对象6.79970703125毫秒Redux Compose函数原理3.6960449604以上代码在MacBook Pro 2019 15寸16G内存512克闪存的铬79下执行,不同的机器不同的环境下执行以上代码都有可能存在差异。
我已同时测试过多台机器和多个浏览器,连续做了10次以上操作,发现减少总体的平均执行时间还是会比其他三个方法稍微快一点,所以大家还是放心使用啦!本文更多是探讨减少的使用技巧,如对减少的兼容和性能存在疑问,可自行参考相关资料进行验证。
最后,送大家一张减少生成的乘法口诀表:一七得七,二七四十八,三八妇女节,五一劳动节,六一儿童节。
更多编程相关知识,请访问:编程视频!以上就是值得了解的25个数组减少高级用法的详细内容,更多请关注我们其它相关文章!
郑重声明:本文由网友发布,不代表盛行IT的观点,版权归原作者所有,仅为传播更多信息之目的,如有侵权请联系,我们将第一时间修改或删除,多谢。