javascript --- 作用域和闭包

执行环境:

// 定义了变量或函数有权访问的其他数据,决定了它们各自的行为
// 每个执行环境都有一个变量对象与之对应,执行环境中所定义的所有变量和函数都保存在变量对象中
// 某个执行环境中的所有代码执行完毕后,该执行环境被销毁,保存在其中的所有变量和函数定义也随之销毁

函数与执行环境:

// 每个函数都有自己的执行环境.当执行流进入一个函数时,函数的环境就会被推入一个环境栈中.
// 在函数执行之后,栈将其环境弹出,把控制权返回给之前的执行环境.

作用域链:

// 当代码在一个环境中执行时,会创建变量对象的一个作用域链.作用域链的用途,是保证对执行环境有权访问的所有变量和函数的有序访问。
// 作用域链的前端,始终都是当前执行的代码(又称为词法作用域)所在环境的变量对象.如果这个环境是函数,则将其活动对象作为变量对象.
// 活动对象在最开始时只包含一个变量,即arguments对象.
// 作用域链中的下一个变量来自包含(外部)环境,而在下一个变量对象来自下一个包含环境.
// 这样,一直延续到全局执行环境;全局执行环境的变量对象始终都是作用域链中的最后一个对象// 参考下面的例子
var color = "blue";
function changeColor() {var anotherColor = "red";function swapColors() {var tempColor = anotherColor;anotherColor = color;color = tempColor;}swapColors();
}
changeColor();
console.log(color); 
// 作用域链的结构如下:
// Window
//    -- color
//    -- changeColor()
//        -- anotherColor
//        -- swapColors()
//            -- tempColor// 一共3个执行环境:全局环境、changeColor()的局部环境和swapColors()的局部环境
// swapColors是changeColor的内部环境,changeColor是全局环境的内部环境
// 通过作用域链,可以从内而外 依次、有序的访问.

下面从最简单的全局作用域开始,深入挖掘各类解析方案从而涵盖JavaScript提供的所有作用域

延长作用域链:

// 1.eval:可以接受一个字符串为参数,并将其中的内容视为好像在书写时就存在于程序中这个位置的代码
function foo(str, a) {eval(str);console.log(a, b);
}
var b = 2;
foo("var b = 3;",1 );// 等价于:
function foo(a) {var b = 3;console.log(a,b,);
}
var b = 2;
foo(1)
// 作用域链
// Window
//    - b
//    - foo
//        - b
//        - a// 2.with:通常被当作重复引用同一个对象中的多个属性的快捷方式:
function foo(obj) {with(obj) {a = 2;  }
};
var o1 = {a: 3
};
var o2 = {b: 3
};
foo(o1);
console.log(o1.a);    // 2foo(o2);
console.log(o2.1);    // undefined
console.log(a);    // 2,泄露到全局上// o2的作用域,foo(...)的作用域和全局作用域中都没有找到标识符a,因此在执行a = 2时,自动创建了一个全局变量
// ps:尽量不用eval 和 with,会影响执行效率!!!

先来看下面的一段代码:

function foo() {var a = 2;function bar () {console.log( a );}return bar;
}
var baz = foo();
baz(); // 2// 1.函数bar()的词法作用域可以访问foo()的内部作用域,
// 2.在foo()执行后,由于javascript引擎的垃圾回收机制会释放不在使用的内存空间.
// 3.闭包,阻止了foo()的内部作用于的释放,原因在于bar()拥有涵盖foo()内部作用域的闭包,使得foo的内部作用域一直存活,以供bar()一直使用// 注:bar()对foo作用域的引用,该引用叫做闭包(闭包可以使得函数继续访问定义时的词法作用域).

参考 《JavaScript高级程序设计》(第3版)P73~P74
参考《你不知道的JavaScript》(上卷)P14~P57

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

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

相关文章

异步下载圆形进度条显示进度

圆形进度条参考链接即可:使用css3实现圆形进度条 需求点击下载后遮罩层显示下载进度: 1.圆形进度条参考以上链接,有点小瑕疵,可更改定位距离实现重合。 2.遮罩层: .lbOverlay{display: none;position: fixed;left: 0;…

javascript基本功

隐式类型转换 var a {_default: 0,toString: function () {return a._default} } if (a 1 && a 2 && a 3) {console.log(解) } 访问一个变量的时候进行拦截 var _default 0 Object.defineProperty(window, a, {get() {return _default} }) if (a 1 &am…

深信服笔试,抓兔子

*问题描述:抓兔子n个排成一排的洞,编号为1到n,兔子每天晚上会跳到相邻的一个洞里,小q每天只能白天检查其中的一个洞,小q会告诉你每天检查的洞,分析是否一定能抓到兔子示例:3个洞,第一…

es6 --- 模块

function foo(){var something cool;var another [1, 2, 3];function doSomething() {console.log( something );}function doAnother() {console.log( another.join( " ! " ) );} } // 是一个不明显的闭包,doSomething()和doAnother()保持了foo的内部作用域接下来…

Java之递归遍历目录,修改指定文件的指定内容

EditProperties.java 1 package PropertiesOperation.Edit;2 3 import java.io.File;4 5 /**6 * 替换指定Porpoerties文件中的指定内容7 * 三个参数:8 * filePath:存放properties文件的目录9 * srcStr:需要替换的字符串 10 * desStr&…

学习日志---7

1.复习Linux hadoop hdfs MapReduce基础知识 1,列举linux常用命令 shutdown now reboot mkdir mkdir -p touch filename rm -r filename rm -rf filename vi filename i--->可编辑状态 esc --> : --->wq 保存退出 q! wq! cat grep find ifconfig ping user…

javascript --- 属性描述符

从ES5开始,所有的属性都具备了属性描述符 var myObject {a: 2 };Object.getOwnPropertyDescriptor(myObject, "a"); //{ // value:2, // writable: true, // 可写 // enumerable: true, // 可枚举 // configurble: true // 可配置 //}定义属性…

看了吗网址链接

sklearn实战-乳腺癌细胞数据挖掘(博主亲自录制视频) https://study.163.com/course/introduction.htm?courseId1005269003&utm_campaigncommission&utm_sourcecp-400000000398149&utm_mediumshare # -*- coding: utf-8 -*- ""&qu…

JMeter 性能测试进阶实战

课程简介 本课程制作的主要目的是为了让大家快速上手 JMeter,期间穿插了大量主流项目中用到的技术,以及结合当今主流微服务技术提供了测试 Dubbo 接口、Java 工程技术具体实施方案,注重实践、注意引导测试思维、拒绝枯燥的知识点罗列、善于用…

javascript --- 混入

显示混入: function mixin(sourceObj, targetObj){for(var key in sourceObj){ // 遍历source中的所有属性if(!(key in targetObj)) { // 找到targetz中没有的属性targetObj[key] sourceObj[key];}}return targetObj; }var Vehicle {engines: 1,iginition: function() {c…

php源码代目录

ext :存放动态和内建模块的目录,在这里可以找到所有的php官方亏站,并且也可以在这里编写扩展; main:包含php的主要宏定义; pear: PHP扩展与应用库; sapi:包含不同服务器抽象层的代码; TSRM:Zend和PHP的"线程安全资源管理器"目录; Z…

bzoj1231 [Usaco2008 Nov]mixup2 混乱的奶牛——状压DP

题目&#xff1a;https://www.lydsy.com/JudgeOnline/problem.php?id1231 小型状压DP&#xff1b; f[i][j] 表示状态为 j &#xff0c;最后一个奶牛是 i 的方案数&#xff1b; 所以下一个只能是和它相差大于 k 而且不在状态中的奶牛。 代码如下&#xff1a; #include<iostr…

JavaScript高级程序设计阅读笔记

2020-11-15 通过初始化指定变量类型 数字-1 对象null和null的比较&#xff08;不理解&#xff09;使用局部变量将属性查找替换为值查找&#xff08;算法复杂度&#xff09;循环的减值迭代&#xff0c;降低了计算终止条件的复杂度switch快多个变量声明逗号隔开使用数组和对象字面…

jquery --- 监听input框失效

使用juery监听Input输入的变化,并且封装起来,如下: // html <input type"text" id‘myinput1’ /> // js function formOnById(id){let dom # id;$(dom).bind(input propertychange,()>{let item $(dom).val;console.log(item);} } formOnById(myinp…

windows任务计划程序 坑

转载于:https://www.cnblogs.com/kaibindirver/p/8109041.html

第三篇:函数之嵌套

1 #函数的嵌套调用&#xff1a;在调用一个函数的时&#xff0c;其内部的代码又调用其他的函数2 # def bar():3 # print(from bar)4 #5 # def foo():6 # print(from foo)7 # bar()8 #9 # foo() 10 11 12 # def max2(x,y): 13 # if x > y: 14 # ret…

vue路由权限(结合服务端koa2)

gitee地址 一、项目初始化 vue create manager-admin // 创建vue项目// 管理员权限安装 cnpm i -S koa2 // 下载koa2依赖 cnpm install --global koa-generator // 下载框架 koa-generator koa2 manager-server // 创建项目 cd manager-server // 进入项目 npm install // 安…

javascript --- 类、class、事件委托的编程风格

类风格: // 父类 function Widget(width, height) {this.width width || 50;this.height height || 50;this.$elem null; } Widget.prototype.render function($where) {if(this.$elem) {this.$elem.css({width: this.width "px",height: this.height "p…

在线获取UUID

http://fir.im/udid转载于:https://www.cnblogs.com/mtjbz/p/8116576.html

堆和堆排序

堆和优先队列 普通队列&#xff1a;FIFO&#xff0c;LILO 优先队列&#xff1a;出队顺序和入队顺序无关&#xff0c;和优先级相关。一个典型应用就是操作系统中。动态选择优先级高的任务执行 堆的实现 最典型的堆就是二叉堆&#xff0c;就像是一颗二叉树。这个堆的特点&#xf…