JavaScript-异常与this处理与性能优化

1. 深浅拷贝

在这里插入图片描述

    const obj = {uname: 'nidie',age: 18}// o对象直接复制obj,直接赋值将obj的地址也给了oconst o = obj// 正常打印18console.log(o);// 对o改动,打印obj,obj也被改动了o.age = 20console.log(o);console.log(obj);

1.1 浅拷贝

在这里插入图片描述
拷贝对象:Object.assgin()
拷贝数组:Array.prototype.concat()

    const obj = {uname: 'nidie',age: 18}// 浅拷贝const o = { ...obj }console.log(o);// 对未改动的obj没有影响o.age = 20console.log(o)console.log(obj);console.log('----------------------');// 利用assign方法浅拷贝const oo = {}Object.assign(oo, obj)oo.age = 20console.log(oo);console.log(obj);console.log('----------------------');// 但是浅拷贝仍然存在问题const objj = {uname: 'nidie',age: 18,family: {baby: 'son'}}const ooo = {}Object.assign(ooo, objj)// 简单数据类型age直接赋值没关系,obj对象中存储的family地址会给oooooo.age = 20ooo.family.baby = '牛魔'// 只想改变ooo的family对象里面的属性,却把objj的也改了console.log(ooo);console.log(objj);

总结:

在这里插入图片描述

1.2 深拷贝

在这里插入图片描述

递归实现深拷贝

在这里插入图片描述

    function getTime() {document.querySelector('div').innerHTML = new Date().toLocaleString()// 每隔一秒调用一次自己setTimeout(getTime, 1000)}getTime()

注意:

  1. 利用函数递归
  2. 普通属性直接赋值,遇到复杂数据类型,数组,对象则调用自己
  3. 数组的逻辑顺序要在对象前面
    const obj = {uname: 'nidie',age: 18,hobby: ['lu', 'lulu'],family: {baby: 'babybaby'}}const o = {}// 将obj拷贝给ofunction deepCopy(newObj, oldObj) {// 遍历旧对象for (let k in oldObj) {// if的逻辑顺序不能反,因为数组也属于对象,必须先筛选完数组再写对象// 处理数组的问题if (oldObj[k] instanceof Array) {// 再次遍历数组newObj[k] = []deepCopy(newObj[k], oldObj[k])}// 处理对象问题else if (oldObj[k] instanceof Object) {// 再次遍历newObj[k] = {}deepCopy(newObj[k], oldObj[k])}else {// k  属性名  oldObj[k] 属性值// newObj[k] === o.unamenewObj[k] = oldObj[k]}}}deepCopy(o, obj) //o新对象 obj旧对象o.age = 20o.hobby[0] = 'bulu'o.family.baby = '牛魔'console.log(o);console.log(obj);

利用库函数直接深拷贝

  <script src="lodash.js"></script><script>const obj = {uname: 'nidie',age: 18,hobby: ['lu', 'lulu'],family: {baby: 'babybaby'}}const o = _.cloneDeep(obj)console.log(o);

利用JSON实现深拷贝

    const obj = {uname: 'nidie',age: 18,hobby: ['lu', 'lulu'],family: {baby: 'babybaby'}}// 把对象转换为JSON字符串console.log(JSON.stringify(obj));// parse方法再将字符串转换为对象const o = JSON.parse(JSON.stringify(obj))console.log(o);o.family.baby = '牛魔'console.log(o)console.log(obj);;

总结

在这里插入图片描述

2. 异常处理

2.1 throw抛异常

在这里插入图片描述

    function fn(x, y) {if (!x || !y) {// throw '你没传参'// 抛出异常并终止程序throw new Error('没传参')}return x + y}console.log(fn());

总结

在这里插入图片描述

2.2 try/catch捕获异常

在这里插入图片描述

<body><p>123</p><script>function fn() {try {const p = document.querySelector('.p')p.style.color = 'red'}catch (err) {console.log(err.message);// 配合throw使用throw new Error('错了吧人才')return}finally {// 不管程序是否正确,一定会执行finnalyalert('你好')}// catch会拦截错误,但是不会中断程序执行  加入return中断程序}fn()</script>
</body>

总结

在这里插入图片描述

2.3 debugger

在这里插入图片描述

3. 处理this

3.1 this指向-普通函数

对于普通函数来说,谁调用,this就指向谁
在这里插入图片描述

总结

在这里插入图片描述

3.2 this指向-箭头函数

箭头函数this一层层往上找,找到最近的对象
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

3.2 改变this

call

在这里插入图片描述

apply

在这里插入图片描述

    const obj = {age: 18}function fn(x, y) {console.log(this);console.log(x + y);return x + y}// 调用函数,并且让fn中的this指向了第一个参数obj// apply第二个参数必须放数组fn.apply(obj, [1, 2])// 本身就是在调用函数,所以返回值就是函数的返回值console.log(fn.apply(obj, [1, 2]));

bind

call()apply()不同的是,bind不会立即调用函数

在这里插入图片描述

    const obj = {age: 18}function fn() {console.log(this);}// bind不会调用函数// 可以改变this指向// 返回值是一个更改过this的函数const fun = fn.bind(obj)fun()// 需求:有一个按钮,点击里面就禁用,2秒钟后开启const btn = document.querySelector('button')btn.addEventListener('click', function () {// 禁用按钮this.disabled = true###setTimeout(function () {// 在普通函数中的话,要将this指向的window改为btnthis.disabled = false}.bind(this), 2000);})

总结

在这里插入图片描述

4. 性能优化

4.1 防抖(debounce)

在这里插入图片描述

  <script src="lodash.js"></script><script>// 鼠标在盒子中滑动,数字显示+1const box = document.querySelector('.box')let i = 1function mouseMove() {// 存在大量消耗性能的代码,dom操作、数据处理,可能造成卡顿box.innerHTML = i++}// box.addEventListener('mousemove', mouseMove)// 利用库函数lodash防抖函数// _.debounce(fun,时间)box.addEventListener('mousemove', _.debounce(mouseMove, 500))</script>
    // 手写防抖函数// 利用setTimeout定时器实现// 1. 声明定时器变量// 2. 每次鼠标移动的时候都要先判断是否有定时器,如果有的话先清除以前的// 3. 如果没有定时器,就开启定时器,存入到定时器变量中// 4. 定时器里面写函数调用function debounce(fn, t) {let timer// return 返回一个匿名函数return function () {if (timer) clearInterval(timer)timer = setTimeout(function () {fn()}, t)}}box.addEventListener('mousemove', debounce(mouseMove, 100))

4.2 节流

在这里插入图片描述

在这里插入图片描述

    // 利用节流实现性能优化// 鼠标在盒子中滑动,数字显示+1const box = document.querySelector('.box')let i = 1function mouseMove() {// 存在大量消耗性能的代码,dom操作、数据处理,可能造成卡顿box.innerHTML = i++}// 利用lodash库实现节流,500ms之后采取一次+1// 语法:_.throttle('mousemove'),_.throttle(mouseMove,500)box.addEventListener('mousemove', _.throttle(mouseMove, 3000))

总结

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/266839.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

深入理解RabbitMQ消息中间件

一、引语 本文将介绍RabbitMQ消息中间件的基本概念、工作原理以及在实际应用中的使用场景。通过阅读本文&#xff0c;您将了解到RabbitMQ如何帮助企业实现高效的异步通信和解耦。 二、消息中间件 1.简介 信息中间件是一种应用于分布式系统的基础软件&#xff0c;它位于各类…

Leetcode 40 组合总和 II

题意理解&#xff1a; 每个数字在每个组合中只能使用 一次 数字可以重复——>难点&#xff08;如何去重&#xff09; 每个组合和target 求组合&#xff0c;对合限制&#xff0c;考虑回溯的方法。——将其抽象为树结构。 树的宽度——分支大小 树的深度——最…

.NET 8 编写 LiteDB vs SQLite 数据库 CRUD 接口性能测试(准备篇)

WebAppDbTest 项目准备 项目准备1、.net cli 创建项目2、nuget 包引用和项目结构2.1、项目添加相关 nuget 包2.2、WebAppDbTest 项目结构 3、项目代码说明3.1、CSharp/C# 类文件说明3.2、json 配置文件说明 4、项目运行预览 数据库 .db 文件准备1、创建 SQLite 数据库1.1、在 W…

vue前端访问Django channels WebSocket失败

现象 前端报错&#xff1a;SSH.vue:51 WebSocket connection to ‘ws://127.0.0.1:8000/server/terminal/120.59.88.26/22/1/’ failed: 后端报错&#xff1a;Not Found: /server/terminal/120.79.83.26/22/1/ 原因 django的版本与channels的版本不匹配&#xff08;django…

IDEA多模块开发-加载模块管理-加快项目加载速度

加快项目加载速度 当一个项目模块数量多起来之后&#xff0c;若所有的模块都同时使用git&#xff0c;maven管控&#xff0c;那么每次Idea打开项目/git切换分支加载时间将会极久 配置git模块 file-setting- Version-Control 管理git控制模块&#xff0c; 对于当前不需要git管…

【Maven教程】(十二):版本管理 ——版本号定义约定及相关概念,自动化版本发布与创建分支,GPG签名 ~

Maven 版本管理 1️⃣ 版本管理的概念2️⃣ Maven 的版本号定义约定3️⃣ 主干、标签与分支4️⃣ 自动化版本发布5️⃣ 自动化创建分支6️⃣ GPG签名6.1 GPG 及其基本使用6.2 Maven GPG Plugin &#x1f33e; 总结 一个健康的项目通常有一个长期、合理的版本演变过程。例如JUn…

分布式之raft一致性算法

1.CAP定理 在一个分布式系统中&#xff0c;CAP三者不可兼得&#xff0c;最多只有两者可以满足&#xff0c;正所谓鱼和熊掌不可兼得 一致性 Consistency&#xff1a;所有的节点在同一时间的数据一致可用性 Availability&#xff1a;服务在正常响应时间内可用分区容错性 Partit…

全新wifi大师独立版4.0.5分销小程序/专业独立版/带流量主+搭建教程

源码简介&#xff1a; 全新wifi大师独立版4.0.5分销小程序&#xff0c;它是专业独立版&#xff0c;而且是带流量主&#xff0c;有搭建教程。 WiFi大师是一款专为商家店内用户设计的WiFi连接小程序。它的出现有效解决了商家在为客户提供WiFi服务的过程中遇到的各种问题&#x…

大数据篇|Hadoop发展史及介绍

文章目录 一、Hadoop介绍1.1、Hadoop是什么 二、Hadoop发展史2.1、创始人2.2、Hadoop发展历史/起源2.3、Hadoop三大发行版本2.3.1、Apache Hadoop2.3.2、Cloudera Hadoop2.3.3、Hortonworks Hadoop 三、Hadoop组成3.1、Hadoop组成3.2、模块3.3、Hadoop特性优点 一、Hadoop介绍 …

ppt编辑密码如何设置?

大家在PPT中设置了限制编辑&#xff0c;发现后面任然可以编辑文件。那么如何将PPT文件设置成禁止修改模式呢&#xff1f;今天分享几个方法给大家。 方法一 将PPT文件直接保存或者另存为一份文件&#xff0c;在保存时&#xff0c;将文件格式选择为PowerPoint图片演示文稿 方法…

关于uniapp X 的最新消息

uni-app x 是什么&#xff1f; uni-app x&#xff0c;是下一代 uni-app&#xff0c;是一个跨平台应用开发引擎。 uni-app x 没有使用js和webview&#xff0c;它基于 uts 语言。在App端&#xff0c;uts在iOS编译为swift、在Android编译为kotlin&#xff0c;完全达到了原生应用的…

【基于LSTM的股票数据预测与分类】

基于LSTM的股票数据预测与分类 引言数据集与爬取数据处理与可视化股票预测与分类Flask页面搭建股票推荐功能创新点结论 引言 股票市场波动剧烈&#xff0c;对于投资者而言&#xff0c;精准的数据预测和分类是制定明智决策的基础。本文将介绍一种基于长短时记忆网络&#xff08…