前言
本文是笔者在业务开发中的一点函数封装技巧的分享总结
如果要用于实际项目,可能需要彦祖们自行改装
注: 本文重在设计思想的分享
在中高级前端面试中,经常会遇到这样的面试题
请你实现一个 call apply bind...
此时有位面试官让你实现一个 findIndexs
可以返回 [index,index1....]
那么我们该如何应对呢?
场景
彦祖们,今天遇到一个业务场景,要根据业务设置 echarts
的饼图颜色
业务上有四种状态,分别是
正常:green
,异常:red
,未知:gray
,警告:yellow
后端返回的数据结构如下
js
const data = [{value:335, name:'正常'},{value:310, name:'异常'},{value:234, name:'未知'},{value:135, name:'警告'}]
对应的 colorList
就是 ['green','red','gray','yellow']
但是后端返回的 data 顺序和个数
是不固定的
可能是
js
[{value:335, name:'正常'}]
也可能是
js
[{value:310, name:'异常'},{value:234, name:'未知'}]
那么我们就要找到对应的颜色,这个时候就可以用到数组的 findIndex
方法了
常规写法
笔者刚开始的写法是这样的
js
const normalIndex = data.findIndex(item=>item.name === '正常')
const errorIndex = data.findIndex(item=>item.name === '异常')
const unknownIndex = data.findIndex(item=>item.name === '未知')
const warningIndex = data.findIndex(item=>item.name === '警告')
colorList[normalIndex] = 'green'
colorList[errorIndex] = 'red'
colorList[unknownIndex] = 'gray'
colorList[warningIndex] = 'yellow'
防御式编程正式开启😅
开始封装
既然我们已经看出来重复调用的次数有点多了
那么能不能把它封装成一个方法,那么就暂时就命名为 findIndexs
吧
我们把它设计成传入多个函数,返回一个数组的形式
函数签名
看下大致的函数签名
js
Array.prototype.findIndexs = function(fn1,fn2,fn2):[index1,index2,index3]
基础版 findIndexs
这里我们默认彦祖们已经对 js 的原型链有了一定的了解
有了大致思路,我们就简单来实现一下
js
Array.prototype.findIndexs = function(...fns) {
const arr = this // 这里要清楚 this 指向的就是调用的数组
// 首先我们判断一下异常情况
if(!Array.isArray(arr) || arr.length === 0) return []
// 当然严谨一点的话,我们还可以判断一下 fns 里面的每个元素是否是函数
return fns.map(fn=>arr.findIndex(fn)) // 这里我们用 map 来遍历 fns,然后调用 findIndex 方法,返回一个数组
}
那么最简单的一个 findIndexs
就实现了
我们来测试一下
js
const [normalIndex,errorIndex,unknownIndex,warningIndex] = data.findIndexs(item=>item.name === '正常',item=>item.name === '异常',item=>item.name === '未知',item=>item.name === '警告')
这样我们就可以一行代码搞定了😊
双指针模式
当然我们还可以继续进行优化
针对这种有头有尾的遍历,我们可以采用双指针模式
来提升遍历效率
js
Array.prototype.findIndexs = function(...fns) {
const arr = this
if(!Array.isArray(arr) || arr.length === 0) return []
// 如果再严谨点 就判断一下fns里面的每个元素是否是函数
let count = fns.length,res=[]
for(let i = 0,j=count-1;i<=j;i++,j--){
if(i===j) res[i] = arr.findIndex(fns[i]) // 奇数长度 中位数只执行一次
else{
res[i] = arr.findIndex(fns[i])
res[j] = arr.findIndex(fns[j])
}
}
return res
}
写在最后
感谢彦祖们的阅读
个人能力有限
如有不对,欢迎指正 🌟 如有帮助,建议小心心大拇指三连🌟