web前端之JavaScrip中的闭包
MENU
- 闭包--笔试-11
- defineReactive函数,利用闭包封装Object.defineProperty()
- 闭包--节流函数--笔试-10
- 闭包的定义
- JavaScript闭包的9大经典使用场景
闭包–笔试-11
function fun() { var n = 9; // js 中强行给一个未声明的变量赋值,// 程序不会报错// 并且会自动在全局创建此变量add = function() { n++;}; return function() { console.log(n); };
};// 把 fun() 执行的结果赋值给 fn 变量
var fn = fun();// 此处调用的是全局的 add 函数,
// 因为全局的 add 函数作用域链引用着 fun 函数作用域对象
// 所以修改的是 fun 里面变量的值
add();
fn(); // 10// 把 fun() 执行的结果赋值给 fn2 变量
// 注意:这里的 fn2 所引用的是 fun() 执行后的地址
// 所以 fn 和 fn2 变量使用的地址是不同,结果也不相同
var fn2 = fun();
fn2(); // 9
add();
add();
fn2(); // 11
fn(); // 10
add();
fn(); // 10
defineReactive函数,利用闭包封装Object.defineProperty()
function defineReactive(data, key, val) {Object.defineProperty(data, key, {// 可枚举enumerable: true,// 可以被配置,比如可以被 deleteconfigurable: true,// getter get() { return val;},// setterset(newValue) {if (val === newValue) return false;val = newValue;}});
};
let obj = {};
defineReactive(obj, 'a', 10); // 设置 a 属性
console.log(obj.a); // 10 访问 a 的值
obj.a = 100; // 改变 a 的值
console.log(obj.a); // 100 访问改变后 a 的值
闭包–节流函数–笔试-10
1、定义
节流函数的作用是在限定的时间内函数只执行一次。
1、按钮提交(可以避免重复提交,当然不只这种方法,将按钮设置为不可用也可以)。
2、scroll、mousehover、mousemove 等触发频率高的时候。
主要的原理就是在闭包内设置一个标记,在限定的时间内这个 flag 设置为 true,函数再次点击则让执行,setTimeout 函数执行以后将 flag 设置为 flase,就可以继续执行 。
2、html
<!DOCTYPE html>
<html><head><meta http-equiv="Content-Type" content="text/html; charset=GBK"></head><body><div class="box" id="div_box" ><button onclick="fn1()">test</button></div></body>
</html>
3、JavaScript
function throttle(fn, delay) {var flag = false;var timer = null;return function() {// 将参数转成数组var args = [].slice.call(arguments, 0); var context = this;// 如果在限定的时间内 flag 是 true 则直接返回,不让执行if(flag) return false;// 函数正在控制中flag = true; // 执行函数fn.apply(context, args);// 清除定时器clearTimeout(timer); timer = setTimeout(function() {// 延时时间过了以后,放开函数控制flag = false; }, delay); }
}function fn() {console.log(123);
}// 绑定节流函数
var fn1 = throttle(fn, 2000);
闭包的定义
定义-01
闭包是指有权访问另一个函数作用域中的变量的函数。
定义-02
闭包是一个拥有许多变量和绑定了这些变量的环境的表达式(通常是一个函数),因而这些变量也是该表达式的一部分。
定义-03
闭包可以让一个函数访问并操作其声明时的作用域中的变量和函数,即使声明时的作用域消失了,也可以调用。
定义-04
闭包是一个定义在其它函数(父函数)里面的函数,它拥有对父函数里面变量的访问权。闭包有三个作用域的访问权。自身的作用域、父作用域和全局作用域。
JavaScript闭包的9大经典使用场景
1、返回值(最常用)
这个很好理解就是以闭包的形式将 name 返回。
function fn() {var name = "hello";return function (){return name;};
};
var fnc = fn();
console.log(fnc()); // hello
2、函数赋值
在闭包里面给fn函数设置值,闭包的形式把name属性记忆下来,执行会输出 hello。
var fn;
function fnc() {var name = "hello";// 将函数赋值给fnfn = function (){return name;};
};
fnc(); // 要先执行进行赋值,
console.log(fn2()); // 执行输出fn2
3、函数参数
用闭包返回一个函数,把此函数作为另一个函数的参数,在另一个函数里面执行这个函数,最终输出 hello。
function fn(){var name = "hello";return function callback() {return name;};
};
var fun = fn(); // 执行函数将返回值(callback函数)赋值给fnc
function func(f) {// 将函数作为参数传入console.log(f()); // 执行函数,并输出
};
func(fun); // 执行输出fun
4、IIFE(自执行函数)
直接在自执行函数里面将封装的函数fn1传给fn2,作为参数调用同样可以获得结果hello。
(function (){var name = "hello";var fn1 = function (){return name;};// 直接在自执行函数里面调用fn2,将fn1作为参数传入fn2(fn1);
})();
function fn2(f){// 将函数作为参数传入console.log(f()); // 执行函数,并输出
};
5、循环赋值
如果不采用闭包的话,会有不一样的情况。
// 每秒执行1次,分别输出1-10
for(var i = 1; i <= 10; i++){(function (j){// j来接收setTimeout(function (){console.log(j);}, j * 1000);})(i); // i作为实参传入
}
6、getter和setter
第一次输出 hello 用setter以后再输出 world ,这样做可以封装成公共方法,防止不想暴露的属性和函数暴露在外部。
function fn() {var name = 'hello',setName = function (n){name = n;},getName = function (){return name;};// 将setName,getName作为对象的属性返回return {setName,getName};
};
var fn1 = fn(); // 返回对象,属性setName和getName是两个函数
console.log(fn1.getName()); // getter
fn1.setName('world'); // setter修改闭包里面的name
console.log(fn1.getName()); // getter
7、迭代器(执行一次函数往下取一个值)
null
var arr = ['aa','bb','cc'];
function incre(arr) {var i = 0;return function (){// 这个函数每次被执行都返回数组arr中 i下标对应的元素return arr[i++] || '数组值已经遍历完';}
}
var next = incre(arr);
console.log(next()); // aa
console.log(next()); // bb
console.log(next()); // cc
console.log(next()); // 数组值已经遍历完
8、首次区分(相同的参数,函数不会重复执行)
null
var fn = (function (){var arr = []; // 用来缓存的数组return function (val){if(arr.indexOf(val) == -1) { // 缓存中没有则表示需要执行arr.push(val); // 将参数push到缓存数组中console.log('函数被执行了', arr);//这里写想要执行的函数} else {console.log('此次函数不需要执行');}console.log('函数调用完打印一下,方便查看已缓存的数组:', arr);};
})();
fn(10);
fn(10);
fn(1000);
fn(200);
fn(1000);
9、缓存
比如求和操作,如果没有缓存,每次调用都要重复计算,采用缓存已经执行过的去查找,查找到了就直接返回,不需要重新计算。
var fn = (function (){var cache = {}; // 缓存对象var calc = function (arr){ // 计算函数var sum = 0;// 求和for(var i = 0; i < arr.length; i++){sum += arr[i];}return sum;};return function (){var args = Array.prototype.slice.call(arguments,0); // arguments转换成数组var key = args.join(","); // 将args用逗号连接成字符串var result, tSum = cache[key];if(tSum){ // 如果缓存有 console.log('从缓存中取:', cache); // 打印方便查看result = tSum;} else {// 重新计算,并存入缓存同时赋值给resultresult = cache[key] = calc(args);console.log('存入缓存:', cache); // 打印方便查看}return result;}
})();
fn(1, 2, 3, 4, 5);
fn(1, 2, 3, 4, 5);
fn(1, 2, 3, 4, 5, 6);
fn(1, 2, 3, 4, 5, 8);
fn(1, 2, 3, 4, 5, 6);
链接
大千世界出品
相关文章:
web前端之JavaScrip中的闭包
MENU 闭包--笔试-11defineReactive函数,利用闭包封装Object.defineProperty()闭包--节流函数--笔试-10闭包的定义JavaScript闭包的9大经典使用场景 闭包–笔试-11 function fun() { var n 9; // js 中强行给一个未声明的变量赋值,// 程序不会报错// 并…...
Windows下命令行启动与关闭WebLogic的相关服务
WebLogic 的服务器类型 WebLogic提供了三种类型的服务器: 管理服务器节点服务器托管服务器 示例和关系如下图: 对应三类服务器, 就有三种启动和关闭的方式。本篇介绍使用命令行脚本的方式启动和关闭这三种类型的服务器。 关于WebLogic 的…...
LeetCode Hot100 169.多数元素
题目: 给定一个大小为 n 的数组 nums ,返回其中的多数元素。多数元素是指在数组中出现次数 大于 ⌊ n/2 ⌋ 的元素。 你可以假设数组是非空的,并且给定的数组总是存在多数元素。 方法一:哈希表 class Solution {public int…...
数据结构:堆的实现思路
我们之前写过堆的实现代码:数据结构:堆的实现-CSDN博客 这篇文章我们了解一下堆到底是如何实现的 1.堆向下调整算法 现在我们给出一个数组,逻辑上看做一颗完全二叉树。我们通过从根节点开始的向下调整算法可以把它调整成一个小堆 向下调…...
结合 DBSCAN 示例代码介绍 DBSCAN
前文为JoyT的科研之旅第一周——科研工具学习及论文阅读收获-CSDN博客 DBSCAN 介绍 DBSCAN(Density-Based Spatial Clustering of Applications with Noise)是一种基于密度的聚类算法,它能够识别出任意形状的簇,并有效地处理噪声…...
vscode 调试jlink
文章目录 软件使用说明1、启动GDB Server2、下载gdb3、vscode配置4、调试 软件 vscodejlink - (JLinkGDBServer.exe)gcc-arm-none-eabi-10-2020-q4-major (arm-none-eabi-gdb.exe) 使用说明 vscode通过TCP端口调用JLinkGDBServer通过jlink连接和操作设备,vscode不…...
微前端实战:打造高效、灵活的前端应用架构
文章目录 一、微前端简介二、微前端的优势1. 高度模块化2. 独立部署3. 易于扩展4. 技术栈无关5. 独立升级 三、微前端的原理四、微前端案例思路《微前端实战》编辑推荐内容简介作者简介目录前言/序言 随着互联网行业的快速发展,前端应用的规模和复杂度也在不断增加。…...
csv文件EXCEL默认打开乱码问题
这里讨论的问题是,当用记事本打开带有中文字符的csv正常时,用excel打开却是乱码。 简单概括就是:编码问题,windows的 excel打开csv文本文件时,默认使用的是系统内的ANSI,在中文环境下就是GB2312。如果写文件…...
C语言之实现贪吃蛇小游戏篇(2)
目录 🎇测试游戏test.c 🎇游戏头文件包含&函数声明snake.h 🎇游戏实现snake.c 🎇测试游戏test.c #define _CRT_SECURE_NO_WARNINGS 1 #include "snake.h" void test() {int ch 0;do{Snake snake { 0 };//创建…...
Comparator接口
Comparator接口 Comparator 是 Java 中用于比较对象的接口。它允许开发者实现自定义的比较逻辑,以用于对对象进行排序或者确定它们的顺序。 主要方法: Comparator 接口中包含一个抽象方法: int compare(T o1, T o2):用于比较两…...
SELinux refpolicy详解(9)
接前一篇文章:SELinux refpolicy详解(8) 三、refpolicy内容详解 上一回讲解了refpolicy源码根目录下的build.conf文件的前一部分内容。本回继续讲解其后一部分。 2. build.conf 文件路径:refpolicy源码根目录/build.conf。 文…...
零基础上手,秒识别检测,IDEA研究院发布全新T-Rex模型
目标检测作为当前计算机视觉落地的热点技术之一,已被广泛应用于自动驾驶、智慧园区、工业检测和卫星遥感等场景。开发者在研究相关目标检测技术时,通常需熟练掌握图像目标检测框架,如通用目标检测框架 YOLO 系列,旋转目标检测框架…...
python每日一题——20旋转图像
题目 给定一个 n n 的二维矩阵 matrix 表示一个图像。请你将图像顺时针旋转 90 度。 你必须在 原地 旋转图像,这意味着你需要直接修改输入的二维矩阵。请不要 使用另一个矩阵来旋转图像。 示例 1: 输入:matrix [[1,2,3],[4,5,6],[7,8,9]]…...
云计算生成式 -给你不一样的音乐推荐新体验
目录 摘要: 正文: 一、亚马逊云与生成式 AI 结合的展望/总结 二、我用亚马逊云科技生成式 AI 产品打造了什么,解决了什么问题 三、未来云端技术发展趋势的见解 四、云端技术未来需要解决的问题 1、如何保护数据安全和隐私? …...
Zabbix 6.0部署+自定义监控项+自动发现与自动注册+部署zabbix代理服务器
Zabbix 6.0 Zabbix 6.0一、关于zabbix1、什么是zabbix2、zabbix工作原理3、zabbix 6.0 特性4、zabbix 6.0 功能组件 二、Zabbix 6.0 部署1、 部署 zabbix 服务端(1) 部署 Nginx PHP 环境并测试(2) 部署数据库(3) 编译安装 zabbix server 服务端(4) 部署 Web 前端,进…...
Docker 简介及其常用命令详解
Docker 简介及其常用命令详解 Docker 自推出以来,已成为开发和运维领域的重要工具。它简化了应用的部署、测试和分发过程,使得容器化技术成为现代软件开发的标准实践。本文将为您提供Docker的基础介绍以及其常用命令的详细讲解。 什么是Docker…...
基于PHP的高中生物学习平台
有需要请加文章底部Q哦 可远程调试 基于PHP的高中生物学习平台 一 介绍 此高中生物学习平台基于原生PHP开发,数据库mysql。系统角色分为用户和管理员。(附带参考设计文档) 技术栈:phpmysqlphpstudyvscode 二 功能 学生 1 注册/登录/注销 2 个人中心 …...
Git多库多账号本地SSH连接配置方法
Git多库多账号本地SSH连接配置方法 一、前言二、环境三、帮助文档四、多环境配置4.1 配置config文件 五、生成RSA秘钥对5.1 ssh秘钥位置5.2 生成秘钥对(公钥、私钥)5.3 添加公钥到GIT用户配置中 六 测试git是否可以使用七、总结 一、前言 在使用Git管理…...
爬虫学习-基础(HTTP原理)
目录 一、URL和URI 二、HTTP和HTTPS (1)HTTP (2)HTTPS (3)HTTP与HTTPS区别 (4)HTTPS对HTTP的改进:双问的身份认证 三、TCP协议 (1)TCP三次握手…...
Gazebo 中为地面和车轮添加摩擦属性
Gazebo 中为地面和车轮添加摩擦属性 Link friction properties not applied from URDF to Gazebo SDFormat Specification Adding friction to model wheels Gazebo中模型自行滑动(后溜)的原因探究 移动机器人在仿真时,一旦以较大的速度启动&…...
【大模型RAG】拍照搜题技术架构速览:三层管道、两级检索、兜底大模型
摘要 拍照搜题系统采用“三层管道(多模态 OCR → 语义检索 → 答案渲染)、两级检索(倒排 BM25 向量 HNSW)并以大语言模型兜底”的整体框架: 多模态 OCR 层 将题目图片经过超分、去噪、倾斜校正后,分别用…...
TDengine 快速体验(Docker 镜像方式)
简介 TDengine 可以通过安装包、Docker 镜像 及云服务快速体验 TDengine 的功能,本节首先介绍如何通过 Docker 快速体验 TDengine,然后介绍如何在 Docker 环境下体验 TDengine 的写入和查询功能。如果你不熟悉 Docker,请使用 安装包的方式快…...
逻辑回归:给不确定性划界的分类大师
想象你是一名医生。面对患者的检查报告(肿瘤大小、血液指标),你需要做出一个**决定性判断**:恶性还是良性?这种“非黑即白”的抉择,正是**逻辑回归(Logistic Regression)** 的战场&a…...
Java多线程实现之Callable接口深度解析
Java多线程实现之Callable接口深度解析 一、Callable接口概述1.1 接口定义1.2 与Runnable接口的对比1.3 Future接口与FutureTask类 二、Callable接口的基本使用方法2.1 传统方式实现Callable接口2.2 使用Lambda表达式简化Callable实现2.3 使用FutureTask类执行Callable任务 三、…...
PL0语法,分析器实现!
简介 PL/0 是一种简单的编程语言,通常用于教学编译原理。它的语法结构清晰,功能包括常量定义、变量声明、过程(子程序)定义以及基本的控制结构(如条件语句和循环语句)。 PL/0 语法规范 PL/0 是一种教学用的小型编程语言,由 Niklaus Wirth 设计,用于展示编译原理的核…...
如何在最短时间内提升打ctf(web)的水平?
刚刚刷完2遍 bugku 的 web 题,前来答题。 每个人对刷题理解是不同,有的人是看了writeup就等于刷了,有的人是收藏了writeup就等于刷了,有的人是跟着writeup做了一遍就等于刷了,还有的人是独立思考做了一遍就等于刷了。…...
【碎碎念】宝可梦 Mesh GO : 基于MESH网络的口袋妖怪 宝可梦GO游戏自组网系统
目录 游戏说明《宝可梦 Mesh GO》 —— 局域宝可梦探索Pokmon GO 类游戏核心理念应用场景Mesh 特性 宝可梦玩法融合设计游戏构想要素1. 地图探索(基于物理空间 广播范围)2. 野生宝可梦生成与广播3. 对战系统4. 道具与通信5. 延伸玩法 安全性设计 技术选…...
基于matlab策略迭代和值迭代法的动态规划
经典的基于策略迭代和值迭代法的动态规划matlab代码,实现机器人的最优运输 Dynamic-Programming-master/Environment.pdf , 104724 Dynamic-Programming-master/README.md , 506 Dynamic-Programming-master/generalizedPolicyIteration.m , 1970 Dynamic-Programm…...
Kafka入门-生产者
生产者 生产者发送流程: 延迟时间为0ms时,也就意味着每当有数据就会直接发送 异步发送API 异步发送和同步发送的不同在于:异步发送不需要等待结果,同步发送必须等待结果才能进行下一步发送。 普通异步发送 首先导入所需的k…...
JavaScript 数据类型详解
JavaScript 数据类型详解 JavaScript 数据类型分为 原始类型(Primitive) 和 对象类型(Object) 两大类,共 8 种(ES11): 一、原始类型(7种) 1. undefined 定…...
