JS进阶 ---day4

文章探讨了JavaScript中的深浅拷贝概念,包括如何通过扩展运算符、Object.assign以及递归实现深拷贝。同时,提到了lodash库的cloneDeep方法。此外,还讲解了异常处理的try/catch机制,以及函数中this的指向和改变this的方法。最后,介绍了防抖和节流技术在事件处理中的应用,以优化性能。
摘要由CSDN通过智能技术生成

深浅拷贝:

浅拷贝:

拷贝对象后,如果里面的属性值是简单数据类型直接拷贝值.

如果属性值是引用数据类型则拷贝的是地址.

语法:

const obj = {
    uname : 'ly',
    age : 18
}

//浅拷贝
const o = { ...obj }
o.age = 20
//其中obj中age为18, o中age为20

const o1 = {}
Object.assign(o1, obj)//obj赋值给o1
o.age = 20
//其中obj中age为18, o1中age为20

深拷贝:

拷贝的是对象,不是地址

常见方法:

1. 通过递归实现深拷贝

const obj = {
    uname : 'ly',
    age : 18,
    hobby : ['ll', 'yy'],
    family : {xixi: 'hhh'}
}
const o = {}

//拷贝函数
function deepCopy(newObj, oldObj) {
    for (let k in oldObj) {
        //处理数组问题
        if(oldObj[k] instanceof Array)
            {
                newObj[k] = []
                //newObj[k] 接收[]
                //oldObj[k] ['ll', 'yy']
                deepCopy(newObj[k], oldObj[k])
            }else if(oldObj[k] instanceof Object)
            {
                newObj[k] = {}
                //newObj[k] 接收{}
                deepCopy(newObj[k], oldObj[k])
            }else{
                //k 属性名 uname, oldObj[k] 属性值
                // newObj[k] === o.uname
                newObj[k] = oldObj[k]
            }
    }
}

deepCopy(o, obj)
//这样就不会互相影响了

注意:

递归容易发生 " 栈溢出 ", 所以必须要加推出条件 return 

先数组再对象,因为数组也是属于对象

2. lodash / cloneDeep

<script src = './lodash.min.js'></script>
const obj = {
    uname : 'ly',
    age : 18,
    hobby : ['ll', 'yy'],
    family : {xixi: 'hhh'}
}

const o = _.cloneDeep(obj)

先通过利用第三方库来使用.

先引用,再使用

3. 通过JSON.stringify()实现

const obj = {
    uname : 'ly',
    age : 18,
    hobby : ['ll', 'yy'],
    family : {xixi: 'hhh'}
}

const o = JSON.parse(JSON.stringify(obj))

注意: 

JSON.parse()是将JSON字符串转化为对象

JSON.stringify()将对象转化为JSON字符串

---

异常处理 : 预估代码执行过程中可能发生的错误.

 throw抛异常:  

throw抛出异常信息, 程序会终止执行.

Error配合使用

try/catch捕获错误信息:

<p> 123</p>
function fn(){
    try {
        //可能发送错误的代码
        const p = document.querySelector('.p')
        p.style.color = 'red'
    }catch(err){
        console.log(err.message)
        throw new Error('出现错误')
        //需要return中断程序
        //return
        }
        finally{
        //不管程序对不对,一定会执行的代码
        alert('hhh')
        }
    }
   fn()

预估发生错误的代码放入try中,

如果try代码中出现错误后,会执行catch代码段,并截获到错误信息.

debugger

---

普通函数this指向 : 谁调用this就指向谁.

箭头函数this指向 : 箭头函数不存在this, 但是默认绑定外层this的值.

改变this: 3个方法可以动态指定普通函数中this指向

1. call() 

fn.call(指定this的指向, 参数1, 参数2...)

2. apply()

fn.apply(指定this的指向, [传递的值,必须包含在数组里面])

3. bind() : 不会调用函数, 但是能改变this指向.

返回值是个函数, 但是这个函数里面的this指向是更改过的.

fn.bind(指定this的指向, 参数1, 参数2...)

const obj = {
    uname = 'll'
}

function fn(){
    console.log('hh')
   }

const fun = fn.bind(obj)

//调用函数
fun()

---

防抖: 单位时间内, 频繁触发事件,只执行最后一次.

手写防抖函数 : 鼠标在盒子上移动,鼠标停止500ms之后,里面数字才会变化+1

function debounce(fn, t){
  let timer;
  // return 返回一个匿名函数
  return function(){
    if(timer) clearTimeout(timer)
    timer = setTimeout(function(){
      fn()
    }, t)
  }
}
box.addEventListener('mousemove', debounce(mouseMove, 500))

节流: 单位时间内, 频繁触发事件, 只执行一次.

function throttle(fn, t){
  let timer = null;
  // return 返回一个匿名函数
  return function(){
    if(!timer) 
    {
      timer = setTimeout(function(){
        fn()
        // 在setTimeout中是无法删除定时器(clearTimeout), 所以只能用timer= null
        timer = null
      }, t)
  }
  }
}
box.addEventListener('mousemove', throttle(mouseMove, 500))

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值