JavaScript实现对象深拷贝的方法(5种)
知识回调(不懂就看这儿!)
知识专栏 | 专栏链接 |
---|---|
JavaScript知识专栏 | https://blog.csdn.net/xsl_hr/category_12024214.html?spm=1001.2014.3001.5482 |
有关JavaScript的相关知识可以前往JavaScript知识专栏查看复习!!
场景复现
在近期的前端学习中,接触到了小程序和uniapp,对于列表或者数据的展示来说,很多情况下是需要限制展示条数的。下面给出一个具体的需求!!
具体需求:卡片区的内容最多展示四条数据
方法:采用JS原生函数获取键值并去重
最终效果:
下面我们来通过代码示例来详细介绍五种常见的去重方法。 👇👇👇
实现数组去重的五种方法
将下面数组去除重复元素(以多种数据类型为例)
const arr = [1, 2, 2, 'abc', 'abc', true, true, false, false, undefined, undefined, NaN, NaN]
1.Set()+Array.from()
Set方法是最简单的方法,因为Set只存储唯一值。
Set
对象:是值的集合,你可以按照插入的顺序迭代它的元素。 Set中的元素只会出现一次,即Set中的元素是唯一的。Array.from()
方法:对一个类似数组或可迭代对象创建一个新的,浅拷贝的数组实例。
const result = Array.from(new Set(arr))
console.log(result) // [ 1, 2, 'abc', true, false, undefined, NaN ]
注意:
- 以上去重方式对NaN和undefined类型去重也是有效的,是因为NaN和undefined都可以被存储在Set中,
- NaN之间被视为相同的值(尽管在js中:NaN !== NaN)。
2.filter() + indexOf()
filter方法会对满足条件的元素存放到一个新数组中,结合indexOf方法进行判断。
filter()
方法:会创建一个新数组,其包含通过所提供函数实现的测试的所有元素。
function removeDuplicate(arr) {
return arr.filter((item, index) => {
return arr.indexOf(item) === index
})
}
const result = removeDuplicate(arr)
console.log(result) // [ 1, 2, 'abc', true, false, undefined ]
注意:
- 这里的输出结果中不包含NaN,是因为indexOf()无法对NaN进行判断,即
arr.indexOf(item) === index
返回结果为false。(测试如下👇👇👇)
const testArr = [1, 'a', NaN]
console.log(testArr.indexOf(NaN)) // -1
3.for 嵌套 for,splice 去重
利用
Object.assign()
, 第一个参数必须是空对象
function unique(arr){
for(var i=0; i<arr.length; i++){
for(var j=i+1; j<arr.length; j++){
if(arr[i]==arr[j]){ //第一个等同于第二个,splice方法删除第二个
arr.splice(j,1);
j--;
}
}
}
return arr;
}
var arr = [1,1,'true','true',true,true,15,15,false,false, undefined,undefined, null,null, NaN, NaN,'NaN', 0, 0, 'a', 'a',{},{}];
console.log(unique(arr))
//[1, "true", 15, false, undefined, NaN, NaN, "NaN", "a", {…}, {…}] //NaN和{}没有去重,两个null直接消失了
双层循环,外层循环元素,内层循环时比较值。值相同时,则删去这个值。
4.利用Map()
Map对象是JavaScript提供的一种数据结构,结构为键值对形式,将数组元素作为map的键存入,然后结合
has()
和set()
方法判断键是否重复。
function removeDuplicate(arr) {
const map = new Map()
const newArr = []
arr.forEach(item => {
if (!map.has(item)) { // has()用于判断map是否包为item的属性值
map.set(item, true) // 使用set()将item设置到map中,并设置其属性值为true
newArr.push(item)
}
})
return newArr
}
const result = removeDuplicate(arr)
console.log(result) // [ 1, 2, 'abc', true, false, undefined, NaN ]
5.利用includes
function unique(arr) {
if (!Array.isArray(arr)) {
console.log('type error!')
return
}
var array =[];
for(var i = 0; i < arr.length; i++) {
if( !array.includes( arr[i]) ) {//includes 检测数组是否有某个值
array.push(arr[i]);
}
}
return array
}
var arr = [1,1,'true','true',true,true,15,15,false,false, undefined,undefined, null,null, NaN, NaN,'NaN', 0, 0, 'a', 'a',{},{}];
console.log(unique(arr))
//[1, "true", true, 15, false, undefined, null, NaN, "NaN", 0, "a", {…}, {…}] //{}没有去重
实际开发问题解决
首先我们来看看后端返回的数据,我们需要将数据的键值获取到,然后渲染到相应的小标签上。
下图绿色的标签即为渲染上去的效果,至于为什么只有两个被渲染了,原因很简单,因为加了某些限制条件,所以第三条数据被筛选掉了。
1.采用Object.keys()获取键值
在之前的文章中,我们讲过如何获取到数组对象的键值。
在实际代码中,我们这样解决:👇👇👇
于是轻松拿到了键值
2.filter() indexOf()筛选有效数据
这里我们拿到的键值并不全是有效值,因为涉及到有的数据不满足条件,所以我们要进行下一步过滤操作。
// 筛选出有效的数据
tagOldList.filter(item => {
contentData[item].filter((itemitem: { issueState: number; }) => {
if(itemitem.issueState != 0 ) {
tagArr.push(item)
}
})
})
筛选过后的结果如下:
我们不难发现,筛选过后的结果有很多重复的元素,因为在对数据进行筛选时使用了push方法,导致很多重复的元素都被装进了数组当中,所以我们需要对数组进行相同元素合并。
3.Set() Array.from()数组去重
tagList = Array.from(new Set(tagArr))
去重之后的效果如下:👇👇
此时,我们拿到了有效且不重复的数据。
以上就是关于实现数组查重的常见方法分享,相信看完这篇文章的小伙伴们一定能运用这些方法在项目开发中。当然,可能有不足的地方,欢迎大家在评论区留言指正!