关于数组排序的相关总结

filter() sort()取最大值

实现匹配确定数值对应费率

近日写项目遇到这样的需求:
根据后端传过来的不同数量对应的费率,在用户点击数量更改时显示相应的折扣后金额。

  1. 关于项目
    • 1 技术栈:vue
  2. 实现
    • 首先考虑的是在用户点击改变折扣费率,
    • data中存储从后台获取的折扣列表rateList
      数据结构(示例):
[
  {id: 1, power: 4, rate: 0.99},
  {id: 2, power: 8, rate: 0.98},
  {id: 3, power: 2, rate: 0.995},
  {id: 4, power: 16, rate: 0.96},
]

方法一

采用数组的filter()方法
没有处理后端返回数据方式(由于公司后端返回数据按照数量排序,前端可以不做排序处理)

  getCurrentRate(v) {
     let arr =  this.rate.filter((item, index) => {
          return v >= item.power
       })
       let len = arr.length-1
       this.currentRate = arr[len]? arr[len].rate:1
   },

以上每次value改变的时候过滤数组,返回值小于等于当前的数组,那么过滤后数组的最后一位就是当前的折扣费率,同时也要考虑到没有匹配的情况下做初始处理,至此实现。

但上述方法问题:

  1. filter()方法 数组中的每个元素都会执行传入的函数,一定程度上会造成浪费
  2. 虽然后端处理了返回的数据,但是我觉得从严谨的角度来讲,还是需要前端做一下数据的处理,首先想到了数组的sort方法进行排序,虽然this.rate是一个数组,但是每一项其实是一个对象,sort()方法是否可以对于数组中对象的某一项按照一定规则进行排序?肯定是可以的。
    sort(fn),fn函数可以返回一个按照特定属性进行排序
let arr = [
    {id: 1, power: 4, rate: 0.99},
    {id: 2, power: 8, rate: 0.98},
    {id: 3, power: 2, rate: 0.995},
    {id: 4, power: 16, rate: 0.96},
]
let compare = function (cls) {
    return function (a, b) {
        return b[cls] - a[cls]
    }
}
let arrNew = arr.sort(compare('rate'))
console.log(arrNew)

方法二

对于排序后数组依次循环对比,一旦小于rate,返回当前rate的上一个值即为当前的rate,并结束当前循环

let currentRate = null//当前折扣
let count = 9 //当前数量
let index = null //对应索引

let getCurrentRate = (count)=>{
    for (let i of arrNew) {
        if (count < arr[i].power) {
            index = i-1
            break
        }

    }
    currentRate = index >= 0 ? arr[index].rate : 1
}
getCurrentRate(count)

for循环以及reduce()对比

for in

for in 可以对Array以及Object循环,可以得到对应的index 以及key 只能遍历“可枚举的属性”
每次迭代操作会同时搜索实例或者原型属性,因此要比其他循环类型慢,一般速度为其他类型循环的 1/7。因此,除非明确需要迭代一个属性数量未知的对象,否则应避免使用 for-in 循环。

  • 打印一个数组会发现数组会有个length属性 (不可枚举)
    在这里插入图片描述
  • 对于数组,index其实是其一个属性,类型是string。假如为数组赋值一个属性,使用for in 循环也可以遍历这个属性,因此建议使用for of 遍历数组

数组

let array1 = ['1','3']
array1.name = 'xh'
for(let k in array1){
    console.log(k) //1 3 xh
     console.log(typeof k)//string
}

对象

let obj = {name:'xm',age:'18'}
for(k in obj){
    console.log(k) //name  age
    console.log(obj[k]) //xm 18
}
  • 另外 for in只可遍历数组存在部分,而for循环则会从头遍历,所以如果对for in 循环处理 效率会提高
let arr1 = []
arr1[3] = 'a'
arr1[100] = 'b'
arr1[300] = 'c'
let counts = 0
for(let i = 0;i < arr1.length; i++){
    counts++;
    console.log(arr1[i])//依次输出,未定义的输出undefined
}
console.log(counts)//301
let arr1 = []
arr1[3] ='a'
arr1[100] ='b'
arr1[300] ='c'
let counts = 0
for(i in arr1){
    counts++;
    console.log(arr1[i])//a b c
}
console.log(counts)//3

改造后:

let arr1 = []
arr1.name = 'xm'
arr1[3] = 'a'
arr1[100] = 'b'
arr1[300] = 'c'
let counts = 0
for(i in arr1){
    counts++
    if (arr1.hasOwnProperty(i) && /^0$|^[1-9]\d*$/.test(i) && i <= 4294967294){
        console.log(arr1[i])
    }
}
console.log(counts)

for of

for of 数组循环可以得到value 不可以对Object循环,而且不会遍历其自定义属性

let array1 = ['1','3']
array1.name = 'xh'
for(let k of array1){
    console.log(k) //1 3
}

为什么要引进 for-of?
forEach 不能 break 和 return;
for-in 缺点更加明显,它不仅遍历数组中的元素,还会遍历自定义的属性,甚至原型链上的属性都被访问到。而且,遍历数组元素的顺序可能是随机的。
所以,鉴于以上种种缺陷,我们需要改进原先的 for 循环。但 ES6 不会破坏你已经写好的 JS 代码。目前,成千上万的 Web 网站依赖 for-in 循环,其中一些网站甚至将其用于数组遍历。如果想通过修正 for-in 循环增加数组遍历支持会让这一切变得更加混乱,因此,标准委员会在 ES6 中增加了一种新的循环语法来解决目前的问题,即 for-of 。
那 for-of 到底可以干什么呢?
跟 forEach 相比,可以正确响应 break, continue, return。
for-of 循环不仅支持数组,还支持大多数类数组对象,例如 DOM nodelist 对象。
for-of 循环也支持字符串遍历,它将字符串视为一系列 Unicode 字符来进行遍历。
for-of 也支持 Map 和 Set (两者均为 ES6 中新增的类型)对象遍历。
总结一下,for-of 循环有以下几个特征:
这是最简洁、最直接的遍历数组元素的语法。
这个方法避开了 for-in 循环的所有缺陷。
与 forEach 不同的是,它可以正确响应 break、continue 和 return 语句。
其不仅可以遍历数组,还可以遍历类数组对象和其他可迭代对象。
但需要注意的是,for-of循环不支持普通对象,但如果你想迭代一个对象的属性,你可以用
for-in 循环(这也是它的本职工作)。
https://blog.csdn.net/ZGhekuiwu/article/details/53728607?utm_medium=distribute.pc_aggpage_search_result.none-task-blog-2allfirst_rank_v2~rank_v25-5-53728607.nonecase&utm_term=reduce%E5%92%8Cfor%E5%BE%AA%E7%8E%AF%E7%9B%B8%E6%AF%94%E8%B0%81%E8%BF%90%E8%A1%8C%E6%9B%B4%E5%BF%AB

forEach()

还是上面的例子

let arr1 = []
arr1.name = 'xm'
arr1[3] = 'a'
arr1[100] = 'b'
arr1[300] = 'c'
let counts = 0
arr1.forEach((item, index) => {
    console.log(item)//a b c
    counts++
})
console.log(counts)//3

这里的 index 是 Number 类型,并且也不会像 for-in 一样遍历原型链上的属性。
所以,使用 forEach 时,我们不需要专门地声明 index 和遍历的元素,因为这些都作为回调函数的参数。
forEach 将会遍历数组中的所有元素 return 以及break(报错) 无效

let arr1 = []
arr1.name = 'xm'
arr1[3] = 'a'
arr1[100] = 'b'
arr1[300] = 'c'
let counts = 0
arr1.forEach((item, index) => {
    counts++
    return item == 'a'
})
console.log(counts)//3

every: 循环在第一次 return false 后返回
some: 循环在第一次 return true 后返回
filter: 返回一个新的数组,该数组内的元素满足回调函数
map: 将原数组中的元素处理后再返回
reduce: 对数组中的元素依次处理,将上次处理结果作为下次处理的输入,最后得到最终结果。

Python网络爬虫与推荐算法新闻推荐平台:网络爬虫:通过Python实现新浪新闻的爬取,可爬取新闻页面上的标题、文本、图片、视频链接(保留排版) 推荐算法:权重衰减+标签推荐+区域推荐+热点推荐.zip项目工程资源经过严格测试可直接运行成功且功能正常的情况才上传,可轻松复刻,拿到资料包后可轻松复现出一样的项目,本人系统开发经验充足(全领域),有任何使用问题欢迎随时与我联系,我会及时为您解惑,提供帮助。 【资源内容】:包含完整源码+工程文件+说明(如有)等。答辩评审平均分达到96分,放心下载使用!可轻松复现,设计报告也可借鉴此项目,该资源内项目代码都经过测试运行成功,功能ok的情况下才上传的。 【提供帮助】:有任何使用问题欢迎随时与我联系,我会及时解答解惑,提供帮助 【附带帮助】:若还需要相关开发工具、学习资料等,我会提供帮助,提供资料,鼓励学习进步 【项目价值】:可用在相关项目设计中,皆可应用在项目、毕业设计、课程设计、期末/期中/大作业、工程实训、大创等学科竞赛比赛、初期项目立项、学习/练手等方面,可借鉴此优质项目实现复刻,设计报告也可借鉴此项目,也可基于此项目来扩展开发出更多功能 下载后请首先打开README文件(如有),项目工程可直接复现复刻,如果基础还行,也可在此程序基础上进行修改,以实现其它功能。供开源学习/技术交流/学习参考,勿用于商业用途。质量优质,放心下载使用。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值