八维教育JavaScript培训Javascript中的作用域 您所在的位置:网站首页 package在java中的作用 八维教育JavaScript培训Javascript中的作用域

八维教育JavaScript培训Javascript中的作用域

2023-03-17 23:25| 来源: 网络整理| 查看: 265

八维教育JavaScript培训Javascript中的作用域,八维教育JavaScript培训。八维教育建校二十余年拥有丰富的JavaScript培训经验,学习JavaScript就来八维教育。JavaScript是Web的编程语言,JavaScript可以更新和更改HTML和CSS,JavaScript可以计算、操作和验证数据。JavaScript是面向对象的脚本语言。万维网使用 HTML、CSS 和JavaScript (JS) 作为其核心技术。JavaScript是一种高级编程语言,广泛用于 Web 开发。它创建于 90 年代中期,此后成为世界上最流行的编程语言之一。

范围是任何编程语言的核心概念:它们控制代码元素的可见性和可访问性。Javascript 和 C++ 等其他语言的概念看似相似,但实际上并非如此。因此,深入了解 Javacript 作用域是值得的。

首先:为什么作用域如此重要?

范围可防止您意外使用或更改范围外的值。

使用库或更大的代码库会让您遇到命名冲突。范围有助于避免这种情况。

如果需要在代码的不同部分之间交换数据,细粒度的范围控制可以帮助您更好地组织这种交换。

在我们深入细节之前,我们应该看看其他语言(如 C++)中的作用域是如何组织的。

C++ 中的作用域

从鸟瞰的角度来看,C++ 中的作用域与 JS 中的作用域类似:全局变量在代码的所有部分都是可见的,而块或函数中定义的变量是局部的,它们只在块内可见。

但是有一些重要的区别:

在 C++ 中,变量定义独立于代码执行,因此执行顺序与作用域无关

变量通常在块外定义,所以定义在块中的任何地方都是有效的。在 JS 中,块作用域只定义作用域的结束位置,而不是开始的位置。

C++ 中的单元分为两个不同的部分:头文件(定义“接口”)和代码文件(包含所有代码和本地定义)。标题可以在其他单元中多次导入,以使“外部”定义可用于其他单元。但是代码只是在一个项目中编译一次。ES6 模块试图模仿这种行为,但实际上并不相同。

Javascript 中的时间范围

Javascript 是一种解释型语言,它有一个根本的区别:执行时间很重要!在编译语言中,所有代码都在执行前被访问。范围定义和代码执行是两个独立的步骤。因此,代码在源代码中的位置或执行时间并不重要。在 Javascript 中,代码执行和作用域定义发生在同一个进程中。代码是一步步执行的,这会影响范围。除非不执行,否则变量定义没有任何效果。我称之为“时间范围”,这会产生奇怪的效果。让我们看一个例子:

这是有效的,尽管 f() 是在“a”之前定义的。在执行 f() 时,“a”已经定义。

这也是有效的,但还有另一个原因:Javascript 使用“提升”,因此在执行代码块之前评估函数名称。在这里我们可以在定义之前访问 f()。

在这里,我们可以通过提升访问 f(),但是 f() 不能访问“a”,尽管 a 是在 f() 之前定义的。时间范围有时会导致意想不到的效果,并使代码难以理解。

C++和HTML中的代码执行

除了 Javascript 未编译这一事实之外,代码执行的方式也存在一些根本差异。同样,我们从 C++ 开始。

在 C++ 中,程序启动后只执行一个函数:main()。当 main() 离开时程序结束,因此程序通常会实现某种事件循环以保持程序运行并做一些有用的事情,直到用户决定结束。

在 Javascript 中,这是不同的,至少如果代码是在浏览器中执行的(并且这仍然是运行 Javascript 的最常见平台)。Javascript 作为 HTML 文件的一部分运行,脚本代码可以嵌入到 HTML 文件的不同位置

在 标签中的 元素内

作为外部 javscript 文件

作为外部模块文件,类似于脚本文件,但遵循不同的规则

元素内部的不同位置与 HTML 元素混合。

执行顺序

浏览器严格地从上到下评估 HTML 页面,所有元素都按照它们在文件中出现的方式进行评估。在文件末尾,评估停止。

我们经常读到,Javascript在HTML 呈现后进行评估,但事实并非如此:执行和呈现只是按照它们在 HTML 文件中的顺序出现。请参阅以下示例:

在 HTML 中创建了两个标题,id 为“headline1”和“headline2”。在两者之间,有一个脚本可以创建一个动态元素。这是结果:

标题一这是动态代码头条二

这证明,脚本是在两个标题之间执行的。这是控制台输出:

该脚本尝试打印两个标题的内容,但在执行时 headline2 尚不存在。因此,在呈现 headline2 之前,脚本显然已执行。

执行顺序 - 对范围的影响

HTML 中的代码执行总是从一个空的全局范围开始。执行代码时,上下文会慢慢填充定义。但是代码的所有部分只有一个上下文。

让我们在一个例子中展示这一点:

变量“a”在头元素中定义,但通过代码执行直到 HTML 文件结束。代码的所有部分共享相同的全局上下文,就好像它们在一个地方一样。甚至变量“b”在外部脚本中定义,但也应用于全局上下文。

ES6 模块:有什么区别?

引入了 ES6 模块以获得更好的代码封装。因此,它们具有本地范围并且仅进行导出,明确标记为“导出”。但是看看,如果调用模块,作用域会发生什么:

(您将需要一个实时服务器来运行此代码,因为模块不会从文件中执行)。由于没有导出任何内容,因此“b”的生命以“schript.js”的范围结束。但是“a”在 script.js 的范围内仍然有效。因此,全局上下文总是被导入到模块中。我按照它们出现的顺序标记了控制台输出。这是控制台输出:

ES6 模块是乱序执行的,因此它们在标准脚本代码完成后运行。重要的是:**变量“a”仍然可以访问并且也会被更新,但是顺序很奇怪。

得到教训

Javascript 中的作用域在很大程度上取决于执行顺序。ES6 模块可以访问父上下文中的所有内容,也可以更改那里的值,但是它们执行的时间很难预测。因此,封装远非完美。

和C++有什么区别

C++ 中的单元总是从干净的上下文开始,它们无法访问主程序的全局上下文。一切都需要明确地导入到模块中才能使用它。在 Javascript 中,你总是需要关心什么是全局定义的。在文件开头调用 ES6 模块没有帮助,因为它们被延迟执行。

最好的建议可能是,让全局上下文始终为空。但是有一些定义,比如“globalThis”或“window”,在渲染任何东西之前就已经存在了。即使可以,也不应从模块中更改此变量以避免出现问题。



【本文地址】

公司简介

联系我们

今日新闻

    推荐新闻

    专题文章
      CopyRight 2018-2019 实验室设备网 版权所有