前端常见的栈溢出报错

什么是栈溢出?

在前端开发中,栈溢出是指JavaScript引擎执行代码时,调用栈(call stack)变得太大,超过了浏览器或JavaScript引擎所分配的栈空间,从而导致栈溢出错误调用栈是一种数据结构,用于存储函数调用的信息,包括每个函数的局部变量参数返回地址

当一个函数被调用时,它的信息被推送到调用栈的顶部,当函数执行完毕时,该信息被弹出。如果在一个递归函数或深度嵌套的函数调用链中,调用栈的深度变得过大,超过了引擎的限制,就会导致栈溢出。

一般产生溢出的原因如下:

(下面将会举例一些常见的错误)

1.递归调用未正确终止

function fn() {return fn();
}
fn();

执行上面的代码出现报错:这是告诉开发者调用栈已经超出了最大限制

上面的函数调用,明显就是有问题的,我们需要确保递归调用有正确的终止条件 

比如我们可以增加传参,设定可以终止的条件,比如:

function fn(count) {console.log(count);if (count <= 0) {return '停止';   //等于小于0时停止递归}return fn(count - 1);  //每次减1
}
fn(10); // 适当的终止条件

2.事件处理函数中的递归调用

我们获取了一个btn实例进行监听点击事件然后触发handleCllick事件,但是点击后进行了无限制触发

document.getElementById('btn').addEventListener('click',function handleClick() {handleClick(); // 递归调用
});

上面的代码需要确保不会无限制地在事件处理函数中触发相同的事件

document.getElementById('myButton').addEventListener('click', 
function handleClick() {// 处理点击事件的逻辑
});

3.深度嵌套的回调函数

报错代码:

function fn(callback) {callback(fn); // 可能导致栈溢出
}fn(function callback1(val) {val(function callback2(val2) {// 更多的嵌套回调});
});

因为函数调用层次太深,函数递归调用时,系统要在栈中不断保存函数调用产生的变量,如果递归调用太深,就会造成栈溢出,这时递归无法返回

为了避免过度嵌套回调函数,可以使用 Promiseasync/await 进行异步控制

function fn() {return new Promise(resolve => {resolve();});
}fn().then(() => fn()).then(() => fn());

4.变量未定义也会栈溢出

变量未定义通常不会导致栈溢出,而是会引发 ReferenceError 错误。栈溢出通常是由于函数调用栈的深度过大导致的。然而,如果在递归中使用未定义的变量,可能会导致递归调用的栈溢出

当未定义x时,x放fn()前面:

function fn(count) {
//未定义x,会报错console.log(count);return x+fn(count - 1)
}fn(5);

 报错如下:

 当未定义x时,x放fn()后面:

function fn(count) {console.log(count);// 忘记定义变量 xreturn fn(count - 1)+ x 
}fn(5);

 报错如下:

由于变量 x 没有被定义,它的值为 undefined。在递归调用中,这可能导致栈溢出,因为每次递归都会尝试访问 fn(...)+undefined,从而形成无限递归

我们需要确保所有变量在使用之前都被正确地定义,并且如果没有终止条件,需要加上。


function fn(count) {if (count === 0) return 0; // 递归出口,不再调用递归函数// 定义变量 `x`let x = 0;console.log(count);return fn(count - 1) + x;
}fn(5);

在实际开发中,为了避免使用未定义的变量,可以使用严格模式 ("use strict") 来帮助捕获未定义的变量

上面说到了严格模式:

简单的了解下什么是严格模式,我们可以通过使用严格模式 ("use strict") 来强制执行更严格的语法错误处理规则,其中包括捕获未定义的变量。

严格模式能够帮助我们更早地发现潜在的问题,因为我们可能有些东西在平时使用中被忽略或者遗忘的。

在Vue 2中,可以在单文件组件或者JavaScript文件顶部启用严格模式,加上"use strict"即可,

请注意,这行代码必须位于文件的最顶部,不能有任何代码出现在它的前面。

如下所示:

例如vue文件中:
<script>
"use strict";export default {// 组件定义
}
</script>
//------------------------------------
单独的纯js文件中:// 在 JavaScript 文件的顶部启用严格模式
"use strict";// 其他代码...

严格模式下会抛出的错误:

1.未定义变量报错: 在严格模式下,如果使用未声明的变量,会抛出 ReferenceError 错误。

2.删除不可删除的属性报错: 在严格模式下,尝试删除一个不可删除的属性会抛出 TypeError 错误。

3.禁止使用 with 语句: 在严格模式下,使用 with 语句会导致语法错误

WITH方法:

 由于大量使用with语句会导致性能下降,同时也会给调试代码造成困难,因此在开发大型应用程序时,不建议使用with语句,现在这个with已经废弃了

with 语句扩展一个语句的作用域链,语法为:

with (expression)  //将给定的表达式添加到在评估语句时使用的作用域链上。表达式周围的括号是必需的。statement  //任何语句。要执行多个语句,请使用一个块语句 ({ ... }) 对这些语句进行分组。

with'语句将某个对象添加到作用域链的顶部,如果在 statement 中有某个未使用命名空间的变量,跟作用域链中的某个属性同名,则这个变量将指向这个属性值。如果沒有同名的属性,则将拋出ReferenceError异常。

使用举例:

使用了JavaScript变量和Math对象的方法来计算。

var a, x, y;
var r = 10;with (Math) {a = PI * r * r;      //圆的面积x = r * cos(PI);     //计算了在极坐标系中半径为 r,角度为 PI 弧度的点的 x 坐标y = r * sin(PI / 2); //计算了在极坐标系中半径为 r,角度为 PI / 2 弧度的点的 y 坐标
}//其中:
with (Math) { ... }: 
这个语句块用于指定之后的代码中的变量或函数来自于 Math 对象。
这样可以省略每次引用 Math 对象的前缀。解决了像:(简单举例)获取对象obj的属性的值原来的:
var a = obj.a;
var b = obj.b;
var c = obj.c;使用with后:
with(obj){var a = a;var b = b;var c = c;
}

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

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

相关文章

【复现】帮管客CRM 客户管理系统 sql注入漏洞_37

目录 一.概述 二 .漏洞影响 三.漏洞复现 1. 漏洞一&#xff1a; 四.修复建议&#xff1a; 五. 搜索语法&#xff1a; 六.免责声明 一.概述 帮管客CRM客户管理系统基于先进的CRM营销理念设计&#xff0c;集客户档案、销售记录、业务往来于一身&#xff0c;以凝聚客户关系…

Vue.js 中子组件向父组件传值的方法

Vue.js 是一款流行的 JavaScript 前端框架&#xff0c;它提供了一套完整的工具和 API&#xff0c;使得开发者可以更加高效地构建交互式的 Web 应用程序。其中&#xff0c;组件化是 Vue.js 的一个核心概念&#xff0c;通过组件化可以将一个复杂的应用程序拆分成多个独立的部分&a…

简述MinewSemi的GNSS模块引领体育与健康科技革新

体育与健康科技领域的创新一直在推动人们更健康、更活跃的生活方式。创新微公司的GNSS模块正成为这一变革的关键推动力。本文将深入研究MinewSemi的GNSS模块在体育和健康追踪领域的创新应用&#xff0c;探讨其如何帮助个体更全面地了解和改善自己的身体状态。 1. 个性化运动轨迹…

UnitySahder实现Phong/BlinnPhong模型

目录 Phong模型公式&#xff1a; BlinnPhong模型公式&#xff1a; 实现&#xff1a; Phong模型&#xff1a; BlinnPhong模型&#xff1a; Phong模型公式&#xff1a; 结果自发光&#xff0b;环境光漫反射高光反射 BlinnPhong模型公式&#xff1a; 对Phong模型的简单修改&…

# Redis 分布式锁如何自动续期

Redis 分布式锁如何自动续期 何为分布式 分布式&#xff0c;从狭义上理解&#xff0c;也与集群差不多&#xff0c;但是它的组织比较松散&#xff0c;不像集群&#xff0c;有一定组织性&#xff0c;一台服务器宕了&#xff0c;其他的服务器可以顶上来。分布式的每一个节点&…

拓扑排序算法

操作对象&#xff1a;AOV网的点和边 有向无环图&#xff1a;有向图且不会形成回路 AOV网&#xff1a;在一个表示工程的有向图中&#xff0c;用顶点表示活动&#xff0c;用弧表示活动之间的优先关系&#xff0c;这样的有向图为顶点表示活动的网&#xff0c;称为AOV网 拓扑排序…

Web3生态系统:构建去中心化的数字社会

随着科技的飞速发展&#xff0c;我们正处在迈向数字未来的道路上&#xff0c;而Web3生态系统则成为这一变革的中心。不仅仅是技术的演进&#xff0c;Web3代表着对传统互联网体系的颠覆&#xff0c;致力于构建一个去中心化的数字社会。本文将深入探讨Web3的核心特征、对金融、社…

2024年美赛A题:资源可用性和性别比例 Resource Availability and Sex Ratios 思路模型代码解析

2024年美赛A题&#xff1a;资源可用性和性别比例 Resource Availability and Sex Ratios 思路模型代码解析 【点击最下方群名片&#xff0c;加入群聊&#xff0c;获取更多思路与代码哦~】 问题翻译 虽然一些动物物种存在于通常的雄性或雌性之外&#xff0c;但大多数物种在很大…

Linux系统Shell脚本-----------正则表达式 文本三剑客之---------grep、 sed

一、正则表达式 1.前言 正则表达式(regular expression)描述了一种字符串匹配的模式&#xff08;pattern&#xff09;&#xff0c;可以用来检查一个串是否含有某种子串、将匹配的子串替换或者从某个串中取出符合某个条件的子串等。在Linux中也就是代表我们定义的模式模板&…

“错误: 不支持发行版本 XX”的解决方法

目录 1 查看Project Structure 1.1 打开Project Structure 1.2 查看Project Setting/Project 1.3 查看 Project Setting/Modules 1.4 查看Platform Setting/SDKs 2 查看Settings 2.1 打开Settings 2.2 查看Java Compiler 2.3 查看Maven/Runner 3 查看pom.xml 1 查…

AI算力专题:华为算力分拆:全球AI算力的第二极

今天分享的是AI算力系列深度研究报告&#xff1a;《AI算力专题&#xff1a;华为算力分拆&#xff1a;全球AI算力的第二极》。 &#xff08;报告出品方&#xff1a;华西计算机团队&#xff09; 报告共计&#xff1a;53页 全球龙头英伟达业绩持续高度景气&#xff0c;印证全球A…

k8s安装dashboard报错CrashLoopBackOff

报错信息 使用kubectl get pods -A查看集群&#xff0c;出现错误&#xff1a; kubernetes-dashboard kubernetes-dashboard-xxxxxxxxxx6-2qrst 0/1 CrashLoopBackOff 6 15m查看日志后&#xff0c;发现原因&#xff1a; panic: Get "https://10…