是否为数组?
Array.isArray(arr)
,不用typeof
(arr为Object);
传统:
Object.prototype.toString.call(arr)=="[object Array]"
;
Array类型的Array.toString()
是Object基础类的封装方法;
深浅克隆
基本类型值:number、string、boolean、undefined;
“==“,”===”比较时,是否值相等;
引用类型值:functioin、object、array、RegExp;
“==“,”===”比较时,是否为同对象;
null为基本类型值,但是typeof
为object
,归类存争议;null === null 为true;
赋值引用:var a = arr1; var b = arr1; a==b==true
浅克隆:var newArr = [].concat(arr)
;var newArr = [...arr]
深克隆:递归
JS Array
arr.push()/unshift() 返回数组长度,新增到末尾/开头;
arr.pop()/shift() 返回被删的元素,删除末尾/开头;
arr.splice(startIndex,length,addArr,…addArr) 剪/接/替换,返回被删数组;
indexOf(obj,startIndex) 从头向尾查;
lastIndexOf(obj,startIndex) 从尾向头查,找不到时,返回-1;
arr.slice(startIndex,endIndex) 剪切返回被切数组,原数组不变;
arr1.concat(arr2,arr3) 拼接;
arr.toString() 默认逗号隔开字符串;
arr.join("+") 指定连接符隔开转字符串;
arr.reverse() 倒序/反转,返回改变数组;
arr.sort() 按规则排序;
扁平化
多层嵌套数组的扁平化,例如[1,2,3,[4,[5,6,7],8],9]
=>[1,2,3,4,5,6,7,8,9]
;
递归遍历数组,concat
合并数组;关键在于遍历数组;
- arr.some()
Arr.some(fo(item,index,arr),callback)
数组遍历每一项传入fo(),item传入回调函数;
如果有一个元素满足条件,则返回布尔值true(剩余的元素不会再执行检测);
function flatten(arr){
//while循环,内部子项有数组,扩展运算符展开concat合并,继续arr进行while循环
while(arr.some(item=>Array.isArray(item))){
arr = [].concat(...arr);
}
return arr;
}
flatten([1,2,[3,4]])//[1,2,3,4]
- arr.map()
Arr.map(fo(item,index,arr),callback)
数组遍历每一项传入fo(),item传入回调函数;
返回新数组,(遍历所有项);
function flatten(arr){
var res = [];
//遍历
arr.map(item=>{
if(Array.isArray(item){
//递归
res.res.concat(flatten(item));
}else{
//推入新数组
res.push(item);
})
})
return res;
}
flatten([1,2,[3,4]])//[1,2,3,4]
- arr.reduce()
Arr.map(fo(result,item,index,arr),initValue)
回调函数fo(),result初始值为initValue;
同样可以遍历数组,concat合并数组;
function flatten(arr){
return arr.reduce((result, item)=>{
//递归
return result.concat(Array.isArray(item)?flatten(item):item);
},[])
}
-
转为字符串分割
arr.join(",").split(",").map()
;
arr.toString().split(",").map()
; -
for循环+递归
排序
arr.sort()
排序数组,按照首字符以0-9A-Za-z排列,特殊符号除外;
arr.reverse()
反转数组,同上规则反转排列;
- 冒泡排序
for嵌套,相邻比较,交换位置,(注意判断交换的条件,先末尾的排好)
//比较几轮
for(let i=0;i<len-1;i++){
//每轮几次
for(let j=0;j<len-i-1;j++){
//arr[j]和arr[j+1]比较
}
}
- 选择排序
for嵌套,序位选出,(先开头的排好)
//比较几轮
for(let i=0;i<len-1;i++){
//每轮几次
for(let j=i+1;j<len-1;j++){
//arr[i]和arr[j]比较
}
}
- 快速排序:二分法
取中间值,一分为二,递归二分为四,直到不能分
function fo(arr){
//最后停止递归循环
if(arr.length<=1){
return arr;
}
let leftArr = [];
let rightArr = [];
let mid = arr.splice(Math.floor(arr.lenght/2),1)
for(var i=0;i<arr.length;i++){
if(arr[i]<=mid){
leftArr.push(arr[i])
}else{
rightArr.push(arr[i])
}
}
//递归 继续二分
return fo(leftArr).concat(mid,fo(rightArr));
}
随机乱序
本质:数组下标的随机;随机删除一个推进新数组,递归;
去重
JavaScript 高性能数组去重
只是整数数组类型,不可全拿,必要情况之下,依赖实测决定方案;
本质:遍历数组;
- arr.filter()/for(of)/arr.forEach()+indexOf()/includes()
arr.filter(fo(currentValue,index,arr), thisValue)
通过fo()返回布尔值,过滤;
for(of)循环,不重复项推进新数组;
let newArr = [];
for(let i of arr){
!newArr.includes(i) && newArr.push(i);
}
return newArr;
- for(i)嵌套
冒泡查询,删除重复性;
//for循环
for(let i=0,len=arr.length;i<len;i++){
for(let j=i+1;j<len;j++){
if(arr[i] == arr[j]){
arr.splice(j,1);
j--;
len--;
}
}
}
return arr;
- arr.sort()
排序后,遍历去重 - new Set()
arr.from(new Set([...a,...b]))
,根据new Set()并集的数据结构arr.from()创建数组,(自动去重) - for(of)+Object
利用自定义对象的属性,标记重复性;
结束后释放内存,垃圾回收机制;
let newArr = []
let obj = {}
for(let i of arr){
if(!obj[i]){
//标记已存在
obj[i] = true;
newArr.push(i);
}
}
并集、交集,差集
new Set(arr1,arr2)
(去重的)并集,
new Set([...arr1].filter(i => b.has(i));
交集
new Set([...arr1].filter( i=> !b.has(i)));
差集