JavaScript 循环方法

news2024/11/29 1:29:58

JavaScript 循环方法

不涉及到具体绑定到 prototype 上的循环方式,即 XXXXX.prototype 中包含的循环方式(如 forEach, map)。

for

for 总共有三种循环方式,一个是传统的 for 循环体,一个是 for in,还有一种是 for of

传统 for

这个语法大多数其他的编程语言也有,JS 中主要是在于变量的声明,如:

// ES5
for (var i = 0; i < 10; i++) {
  console.log('es5');
}

// ES6
for (let i = 0; i < 10; i++) {
  console.log('es6');
}

const arr = [1, 2, 3];

for (let i = 0; i < arr.length; i++) {
  console.log(arr[i]);
}

这里语法没有什么特别大的区别,输出结果也都一致,主要区别就在于 varlet 造成的作用域和变量提升(hoisting)的问题。鉴于目前浏览器对于 ES6 的支持都挺好的,建议使用 let 而非 var

这里不能使用 const,因为使用 const 声明的变量无法被修改,所以这里也就无法被 increment,从而导致报错:

在这里插入图片描述

var, let, const 的异同可以查看这篇笔记:var, let, const 的区别与相同

另外一个比较有趣的写法,也是之前没有注意到的,就是省略所有变量声明的写法:

for (;;) {
  // do sth
}

这样会造成一个无限循环。

for...of

for...of 是一个 ES6 后实现的迭代方式,大多数情况下用来便利数组,不过它本身可以用来循环所有的 iterable 对象,其中包括:

  • 数组
  • 字符串
  • TypedArray
  • Map
  • Set
  • NodeList
  • arguments
  • generators
  • 用户自定义的 iterable 对象

总体来说如果是搭配 ES6 以后新创建的一些 objects 与特性,其灵活度甚至比起传统 for 循环还要高,唯一的局限就在于无法获取下标。

下面是比较常见使用 for...of 的语法:

const arr = [1, 2, 3, 4, 5];

for (const val of arr) {
  console.log(val);
}

const map = new Map([
  ['a', 1],
  ['b', 2],
  ['c', 3],
]);

for (const [key, val] of map) {
  console.log(key, val);
}

const set = new Set(['a', 1, 'b', '2', 2]);

for (const setV of set) {
  console.log(setV);
}

在这里插入图片描述

for...in

for...in 用于迭代对象中不包括 symbol 的可枚举字符串属性 enumerable string properties,并且,for...in 也可以用来迭代继承的可枚举字符串属性:

const obj = {
  a: 'a',
  b: 'b',
  c: 'c',
};

for (const enumerable in obj) {
  console.log(enumerable);
}

const obj2 = { d: 'd' };
obj2.__proto__ = obj;

for (const enumerable in obj2) {
  console.log(enumerable);
}

在这里插入图片描述

while

while 主要就分 whiledo-while,二者的区别不算太大,主要是 do-while 会至少运行一次再检测是否满足条件。

let i = 10;

while (i < 0) {
  console.log('i < 10');
}

do {
  console.log('at least log once');
} while (i < 10);

在这里插入图片描述

关键字

主要补一下 label……才发现原来 JS 也有啊……

break

break 可以用来打破当前的循环,换言之,如果在 nested loops 中,它会 break inner loop:

for (let i = 0; i < 5; i++) {
  console.log('i', i);
  for (let j = 0; j < 20; j++) {
    // 这里一旦 j > 1 就会跳出当前循环
    if (j > 1) break;
    console.log('j', j);
  }
}

在这里插入图片描述

continue

continue 会继续下一个循环,如:

for (let i = 0; i < 5; i++) {
  // 一旦 i > 2,就会跳过下面的代码,重新进入循环
  if (i > 2) continue;
  console.log('i', i);
  for (let j = 0; j < 20; j++) {
    if (j > 1) break;
    console.log('j', j, 'i', i);
  }
}

在这里插入图片描述

label

label 之前我没怎么用过……好像只有在汇编的时候碰到过。

其主要用途是将一个 label 绑定一个 expression,随后跳到对应的 label 上。虽然非循环体也可以使用 label,不过大多数情况下还是循环体中比较符合使用规律:

for (let i = 0; i < 3; i++) {
  let j = 3;
  outer: do {
    console.log(j);
    for (let k = 0; k < 5; k++) {
      // 一旦k === 3 就会跳到 outer,因为 outer 的条件不满足了,所以就会彻底终止 do-while 循环
      if (k === 3) {
        break outer;
      }
      console.log(k);
    }
    j++;
  } while (j < 3);
}

在这里插入图片描述

ES6 后的其他循环方式

map 可以使用其本身提供的 keys()values() 两个函数,set 则是只有 values。它们返回的都是 iterator,所以需要使用 iterator 的方法进行调用。

对象除了 for...in 之外还可以使用 Object.entries(), Object.keys(), Object.values() 的方式获取数组形式的键值对、键和值,因为返回的都是数组,所以可以使用传统的 for 循环。

the end

传统 for 循环写起来可能是最麻烦的,不过对于需要下标的循环来说灵活度也是最高的,在一些情况下确实能够解决 forEach 所带来的问题,不过传统 for 循环无法实现对于对象的循环。

for...of 的写法更加的简单,并且也可以使用 await 进行异步操作,并且搭配一些 ES6 后存在的 objects 与 attributes,其灵活性会更高,不过需要 index 的时候 for...of 就有它的局限性。

for...in 只能用来循环对象,关于什么时候使用获取对象的键值对的方法,可以参考这张表:

在这里插入图片描述

一些其他关于数组循环的笔记有:

  • JavaScript 循环中调用异步函数的三种方法,及为什么 forEach 无法工作的分析

  • JavaScript 的 foreach 用不了 break/continue?同样写法下 for 循环也不行

其他的 reference:

  • for…of

  • for…in

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

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

相关文章

微信最新版本解除【文件只读】

问题 某一天开始&#xff0c;微信自动升级到3.9版本&#xff0c;最大的改变就是接收到的文件是只读属性&#xff0c;网上目前有两个办法&#xff0c;1.降到3.8甚至更早版&#xff1b;2.将version.dll补丁文件复制到微信安装目录&#xff0c;但3.9.2版本就不能用了。 解决办法…

软件测试之测试用例的设计

1. 测试用例的概念 软件测试人员向被测试系统提供的一组数据的集合&#xff0c;包括 测试环境、测试步骤、测试数据、预期结果 2. 为什么在测试前要设计测试用例 测试用例是执行测试的依据 在回归测试的时候可以进行复用 是自动化测试编写测试脚本的依据 衡量需求的覆盖率…

完全了解FPC柔性电路板,生产到市场全讲解

1.什么是FPC 随着社会的不断进步&#xff0c;电子行业的不断更新换代&#xff0c;传统的PCB已经不能满足所有电子产品的需求&#xff0c;FPC的市场需求也越来越大&#xff0c;有很多朋友还不是很清楚FPC是什么&#xff0c;下面来简单的介绍一下: FPC全称&#xff1a;柔性印制电…

利用Springboot来驱动开发桌面程序

众所周知&#xff0c;SpringBoot是一款强大的Javaweb开发程序&#xff0c;这得益于其构造了一个Spring容器&#xff0c;然后通过依赖注入和控制反转&#xff0c;维护起一套Java对象和实例的管理机制&#xff0c;方便开发者去使用。在web应用开发的应用中&#xff0c;Springboot…

python 的垃圾回收机制

一、 引入 python解释器在执行到定义变量的语法时&#xff0c;会申请内存空间来存放变量的值&#xff0c;而内存的容量是有限的&#xff0c;这就涉及到变量值所占用内存空间的回收问题&#xff0c;当一个变量值没有用了&#xff08;简称垃圾&#xff09;就应该将其占用的内存给…

【Linux】IO多路转接-poll

文章目录 I/O多路转接-pollpoll初识poll函数poll的小测试-监控标准输入poll服务器poll_server.cc poll的优点poll的缺点 I/O多路转接-poll poll初识 poll也是系统提供的一个多路转接接口, poll系统调用也可以让我们的程序同时监视多个文件描述符上的事件是否就绪,和select的定…

DDos攻击概述

1.def&#xff1a; 通过大规模互联网流量淹没目标服务器或其周边基础设施&#xff0c;以破坏目标服务器、服务或网络正常流量的恶意行为 目标服务器类比作商店&#xff1b; 网络的正常流量类比作顾客&#xff1b; 此恶意行为便相当于让一堆小混混装成正常顾客涌入商店&…

软件自动化测试有什么优势?自动化测试框架有哪些?

一、 软件自动化测试的优势 在软件测试过程中&#xff0c;自动化测试不断被提高到更高的级别&#xff0c;以提高测试效率以及降低测试成本。 1.节省时间和成本 手动测试需要耗费大量的时间和精力&#xff0c;而自动化测试可以在较短时间内执行多次测试&#xff0c;并且可以在…

Alibaba Sentinel整合SpringBoot,为微服务保驾护航!

前言 随着微服务的流行&#xff0c;服务和服务之间的稳定性变得越来越重要。Sentinel 是面向分布式、多语言异构化服务架构的流量治理组件&#xff0c;主要以流量为切入点&#xff0c;从流量路由、流量控制、流量整形、熔断降级、系统自适应过载保护、热点流量防护等多个维度来…

08-05 应用层设计

伸缩性的架构设计——服务器集群的伸缩性 DNS负载均衡 DNS服务器将访问的域名转发到对应的网关&#xff0c;网关层做反向代理。 利用消息组件对业务场景进行解耦 适合用消息组件解耦的场景 长任务&#xff08;时间长&#xff0c;逻辑复杂&#xff0c;可异步&#xff09…

React Antv G2Plot 「指标拆解图」 前端可视化实战 实现渲染、重置、筛选功能

背景 实现对指定数据的「指标拆解图」 渲染&#xff0c;并且可以根据筛选项进行变化。 任务分解 antv 的图表&#xff0c;以及请求后端的载荷对传入的数据结构有严格要求 一个工具函数将后端接口返回的数据格式化成 antv 图表要求的格式一个工具函数将前端提交的请求数据格…

Copilot入门

文章目录 简介安装初试快捷键取消订阅参考文献 简介 Copilot 是一款 GitHub 和 OpenAI 合作开发的 AI 结对编程工具&#xff0c;支持 Visual Studio、Neovim、VS Code、JetBrains IDEs&#xff0c;用于自动补全代码。 本文以 Python PyCharm 为例。 安装 GitHub Copilot&am…

【数据结构】栈及其实现

目录 &#x1f920;前言 什么是栈&#xff1f; 栈的定义及初始化 栈的定义 栈的初始化 栈的判空 栈顶压栈 栈顶出栈 栈的数据个数 栈的销毁 完整代码 总结 &#x1f920;前言 学了相当长一段时间的链表&#xff0c;总算是跨过了一个阶段。从今天开始我们将进入栈和…

什么是AIGC

AIGC是人工智能创意生成的缩写&#xff08;Artificial Intelligence Generated Creativity&#xff09;&#xff0c;指的是利用人工智能技术实现的创意生成。通俗来说&#xff0c;就是让机器产生新颖、独特且有创造性的作品或方案&#xff0c;例如音乐、绘画、视频、文本等等。…

Sui基金会宣布面向APAC的Office Hours计划

诚挚邀请构建者与Sui基金会的Growth团队一起开启“Office Hours”计划&#xff0c;共同努力&#xff0c;迈向业务增长的下一步。 Sui基金会致力于推动Sui在全球范围内的普及。为此&#xff0c;我们通过积极支持开发人员的开发者资助计划、Builder House和大使计划在Sui上开始…

如何高效运行Omniverse,无惧本地硬件压力

无论是创造能够表达原始情感的逼真数字人&#xff0c;还是构建身临其境的虚拟世界&#xff0c;全球设计、工程、创意和其他行业的人士都在通过3D工作流&#xff0c;突破技术壁垒并拓展创意可能&#xff0c;让虚拟世界和现实世界交融与观众产生共鸣。 而在众多连接未来创作内容的…

ES6中函数新增的方式方法

1.1函数形参的默认值 1.1.1基本用法 ES6 之前&#xff0c;不能直接为函数的参数指定默认值&#xff0c;只能采用变通的方法。如下代码&#xff1a; function func(x,y){y y || "tom";console.log(x,y);}func("hello"); //hello tomfunc("…

数据库标准化之核心结局变量集(COS)

COS介绍 核心结果集&#xff08;COS&#xff09;是在特定健康状况下进行的所有临床试验中应测量和报告的一组最少结局变量集。COS数据库是这些变量集的集合&#xff0c;这些集合是通过循证和迭代过程开发的。该数据库由COMET倡议维护&#xff0c;该计划是研究人员&#xff0c;…

Linux 系统上 C 程序的编译与调试 2 总结

1.gcc分布编译链接 &#xff08;1) 预编译 : gcc -E main.c -o main.i (2) 编译&#xff1a; gcc -S main.i -o main.s (3) 汇编&#xff1a; gcc -c main.s -o main.o (4) 链接&#xff1a; gcc main.o -o main gcc -E hello.c -o hello.i #预处理 gcc -S hello.i -o h…

【FMC134】ADC12DJ3200之4通道3.2GSPS(2 通道6.4GSPS) 12 位AD高速采集子卡设计原理图及调试经验

板卡概述 FMC134 是一款4 通道3.2GSPS&#xff08;或者配置成2 通道6.4GSPS&#xff09;采样率的12 位AD 采集FMC子卡模块&#xff0c;该板卡为FMC标准&#xff0c;符合VITA57.4 规范&#xff0c;可以作为一个理想的IO 模块耦合至FPGA 前端&#xff0c;射频模拟信号数字化后通过…