一、全排列
要求:以数组的方式返回字符串参数的所有排列组合
注意:1.字符串中的参数无重复且全部为小写
2.返回的排列组合数组不区分顺序
难点:递归
const _permute=(string)=>{
let result=[];
let map=new Map();
let dfs=(path)=>{
if(path.length==string.length){
result.push(path)
return
}
for(let i=0;i<string.length;i++){
if(map.get(string[i])) continue
map.set(string[i],true)
path+=string[i]
dfs(path)
map.set(string[i],false)
path=path.substring(0,path.length-1)
}
}
dfs('')
return result
}
console.log(_permute('abc'))//[ 'abc', 'acb', 'bac', 'bca', 'cab', 'cba' ]
二、instanceof
-
如果 target 为基本数据类型直接返回 false
-
判断 Fn.prototype 是否在 target 的隐式原型链上
-
难点:原型链及原型对象
-
const _instanceof=(target,Fn)=>{ //先判断是否为基础数据类型 if(target===null||(typeof(target)!=='object' && typeof(target)!=='function')){ return false } //判断Fn的原型对象在不在terget的原型链上 在target的原型链上一级一级往上找 //target.__proto__...__proto__ 直到找到null 如果中间有相等的值证明在 否则不在 let proto=target.__proto__ while(true){ if(proto===null) return false if(proto===Fn.prototype) return true proto=proto.__proto__ } } function A(){} const a=new A() console.log(_instanceof(a,A))//true console.log(_instanceof(1,A))//false
三、Array.prototype.map -
map 中的 exc 接受三个参数,分别是: 元素值、元素下标和原数组
-
map 返回的是一个新的数组,地址不一样
-
//不能用箭头函数 会改变this的指向 //以函数作为形参 在函数内部调用 //实例方法挂载在Array的原型对象上(Array.prototype) //map=>映射 不改变原数组 Array.prototype._map=function(exc){ const result=[] let index=null let item=null let array=this //实例方法中this指向调用实例方法的变量 for(let i=0;i<array.length;i++){ index=i item=array[i] result.push(exc(item,index,array)) } return result } const arr1=[1,2,3] console.log(arr1._map(item=>item*2)) //[2,4,6]
四、Array.prototype.filter
-
filter 中的 exc 接受三个参数,与map一致,主要实现的是数组的过滤功能,会根据 exc 函数的返回值来判断是否“留下”该值。
-
filter 返回的是一个新的数组,地址不一致。
-
Array.prototype._filter=function(exc){ const result=[]; let index=null; let item=null; let array=this; for (let i=0;i<array.length;i++) { index=i; item=array[i] if(exc(item,index,array)) result.push(item) } return result } let arr=[1,2,3,4] console.log(arr._filter(item=>item%2==0))//[ 2, 4 ]
五、Array.prototype.reduce
-
reduce 接受两个参数,第一个为 exc 函数,第二个为初始值,如果不传默认为 0
-
reduce 最终会返回一个值,当然不一定是 Number 类型的,取决于你是怎么计算的,每次的计算结果都会作为下次 exc 中的第一个参数
-
Array.prototype._reduce=function(exc,init=0){ let prev=init let cur=null; let index=null; let array=this; for(let i=0;i<array.length;i++){ cur=array[i]; index=i; prev=exc(prev,cur,index,array) } return prev } let arr=[1,2,3,4,5] console.log(arr._reduce((prev,cur)=>prev*cur,1))//120
六、Object.create
- Object.create() 方法用于创建一个新对象,使用现有的对象来作为新创建对象的原型(prototype)
-
Object._create=function(proto){ const Fn=function(){} Fn.prototype=proto return new Fn() } function A(){} let obj1=Object.create(A) let obj2=Object._create(A) console.log(obj1.__proto__===A)//true console.log(obj2.__proto__===A)//true
七、浅拷贝
-
const _shallowClone=(target)=>{ if(typeof targer ==='object'&& target == null) { return target }else{ const constructor=target.constructor //constructor if(/^(RegExp|Function|Date|Map|Set)$/i.test(constructor.name)) return target const result = Array.isArray(target) ? [] : {} for (var key in target) { result[key]=target[key] } return result } } const val={ a:0,b:1} console.log(_shallowClone(val))//{ a: 0, b: 1 }
八、深拷贝
-
if(typeof targer !=='object'|| target == null) { return target }else{ const constructor=target.constructor //constructor if(/^(RegExp|Function|Date|Map|Set)$/i.test(constructor.name)) return new constructor(target) if (map.get(target)) return map.get(target) map.set(target,true) const result = Array.isArray(target) ? [] : {} for (var key in target) { if(target.hasOwnProperty(key)){ result=_deepClone(target[key],map) } } return result } } const val={ a:{c:2},b:[1,2,3]} console.log(_deepClone(val))//{ a: { c: 2 }, b: [ 1, 2, 3 ] }
就先到这吧,快看不懂了...